"ওহ, আপনি আছেন! আপনি কি মনে রেখেছেন যে আজ আমাদের আরেকটি পাঠ আছে?"

"না, আমি শুধু তোমাকেই খুঁজছিলাম। প্রায়..."

"চমৎকার, তাহলে শুরু করা যাক। আজ আমি আপনাকে লগিং সম্পর্কে বলতে চাই।"

"লগটি ঘটে যাওয়া ইভেন্টগুলির একটি তালিকা। প্রায় একটি জাহাজের লগ বা একটি ডায়েরির মতো। অথবা টুইটার - সম্ভবত আপনি এটির সাথে আরও ভাল সম্পর্ক করতে পারেন। আশ্চর্যজনকভাবে, একটি লগার হল এমন একটি বস্তু যা আপনি লগিংয়ের জন্য ব্যবহার করেন।"

"প্রোগ্রামিং-এ, প্রায় সবকিছুই লগ করার প্রথা। এবং জাভাতে, আমরা সবকিছু লগ করি এবং এমনকি আরও কিছু।"

"সত্যি হল যে জাভা প্রোগ্রামগুলি প্রায়শই একটি UI, কনসোল ইত্যাদি ছাড়াই বড় সার্ভার অ্যাপ্লিকেশন। তারা একই সময়ে হাজার হাজার ব্যবহারকারীর অনুরোধ প্রক্রিয়া করে এবং প্রায়শই বিভিন্ন ত্রুটি থাকে। বিশেষ করে যখন বিভিন্ন থ্রেড একে অপরের সাথে হস্তক্ষেপ করতে শুরু করে।"

"আসলে, এই পরিস্থিতিতে খুব কমই পুনরুত্পাদনযোগ্য বাগ এবং ব্যর্থতার জন্য অনুসন্ধান করার একমাত্র উপায় হল প্রতিটি থ্রেডে ঘটে যাওয়া সমস্ত কিছু লগ করা।"

"প্রায়শই, লগে মেথড আর্গুমেন্ট, ধরা পড়া ত্রুটি এবং অনেক মধ্যবর্তী তথ্যের তথ্য থাকে।"

"লগটি যত বেশি সম্পূর্ণ হবে, ঘটনাগুলির একটি ক্রম পুনরুত্পাদন করা এবং ব্যর্থতা বা ত্রুটির কারণগুলি ট্র্যাক করা তত সহজ।"

"কখনও কখনও লগগুলি প্রতিদিন কয়েক গিগাবাইটে পৌঁছায়। এটি স্বাভাবিক।"

"কয়েক গিগাবাইট? O_o"

"হ্যাঁ। প্রায়শই, লগ ফাইলগুলি প্রাসঙ্গিক তারিখের ইঙ্গিত সহ স্বয়ংক্রিয়ভাবে সংরক্ষণাগারভুক্ত হয়।"

"হুও।"

"উহ-হু। প্রাথমিকভাবে, জাভার নিজস্ব লগার ছিল না। ফলস্বরূপ, বেশ কয়েকটি স্বাধীন লগার লেখা হয়েছিল। এর মধ্যে সবচেয়ে সাধারণ ছিল log4j।"

"কয়েক বছর পরে, জাভা তার নিজস্ব একটি লগার পেয়েছিল, কিন্তু এর কার্যকারিতা অনেক নিকৃষ্ট ছিল এবং এটি ব্যাপকভাবে ব্যবহৃত হয়নি।"

"এটি সত্য যে জাভাতে একটি অফিসিয়াল লগার আছে, কিন্তু জাভা প্রোগ্রামারদের সমগ্র সম্প্রদায় অন্যান্য লগার ব্যবহার করতে পছন্দ করে। "

"পরবর্তীতে, log4j এর উপর ভিত্তি করে আরো বেশ কিছু লগার লেখা হয়েছে।"

"তারপর বিশেষ সার্বজনীন লগার slf4j, যা এখন ব্যাপকভাবে ব্যবহৃত হয়, তাদের সকলের জন্য লেখা হয়েছিল। এটি log4j-এর মতোই, তাই লগিং ব্যাখ্যা করার সময় আমি এটিকে উদাহরণ হিসেবে ব্যবহার করব।"

"সম্পূর্ণ লগিং প্রক্রিয়া তিনটি অংশ নিয়ে গঠিত।"

" প্রথমে তথ্য সংগ্রহ করুন।"

" দ্বিতীয় , সংগৃহীত তথ্য ফিল্টার করুন।"

" তৃতীয় , নির্বাচিত তথ্য রেকর্ড করুন।"

"আসুন সংগ্রহের সাথে শুরু করা যাক। এখানে একটি ক্লাসের একটি সাধারণ উদাহরণ যা লগ করে:"

লগিং সহ ক্লাস
class Manager
{
 private static final Logger logger = LoggerFactory.getLogger(Manager.class);

 public boolean processTask(Task task)
 {
  logger.debug("processTask id = " + task.getId());
  try
  {
   task.start();
   task.progress();
   task.compleate();
   return true;
  }
  catch(Exception e)
  {
   logger.error("Unknown error", e);
   return false;
  }
 }
}

"লাল রঙে হাইলাইট করা শব্দগুলিতে মনোযোগ দিন।"

" লাইন 3  - লগার অবজেক্ট তৈরি করুন। প্রায় প্রতিটি ক্লাসে এই ধরনের একটি স্ট্যাটিক অবজেক্ট তৈরি করা হয়! ঠিক আছে, ক্লাস ব্যতীত যেগুলি ডেটা স্টোর করা ছাড়া অন্য কিছু করে না।"

" LoggerFactory হল লগার তৈরির জন্য একটি বিশেষ শ্রেণী, এবং getLogger হল এর একটি স্ট্যাটিক পদ্ধতি। বর্তমান বস্তুটি সাধারণত পাস করা হয়, তবে বিভিন্ন বিকল্প সম্ভব।"

" লাইন 7 - মেথড কল সম্পর্কে তথ্য লগারে লেখা হয়। মনে রাখবেন যে এটি পদ্ধতির প্রথম লাইন। মেথডটি কল করার সাথে সাথে আমরা লগে তথ্য লিখি।"

"আমরা ডিবাগ পদ্ধতি বলি, যার অর্থ তথ্যের গুরুত্ব হল ডিবাগ স্তর। এটি ফিল্টারিংয়ের জন্য ব্যবহৃত হয়। আমি আপনাকে কয়েক মিনিটের মধ্যে এটি সম্পর্কে বলব।"

" লাইন 17 - আমরা একটি ব্যতিক্রম ধরি এবং... অবিলম্বে এটি লগে লিখি! ঠিক এটিই করা দরকার।"

"এবার আমরা ত্রুটি পদ্ধতি কল করি, যা অবিলম্বে নির্দেশ করে যে তথ্যটি ERROR স্তর"

লগার- ১

"আপাতত সবকিছু পরিষ্কার বলে মনে হচ্ছে। ঠিক আছে, আমাদের কথোপকথনের মাঝখানে যতটা স্পষ্ট হতে পারে।"

"দারুণ, তাহলে বার্তা ফিল্টারিংয়ের দিকে এগিয়ে যাওয়া যাক।"

"সাধারণত, প্রতিটি লগ বার্তার নিজস্ব গুরুত্ব স্তর থাকে, যা আপনি কিছু বার্তা বাতিল করতে ব্যবহার করতে পারেন। এখানে আমি উল্লেখ করেছি গুরুত্বের স্তরগুলি:"

গুরুত্ব স্তর বর্ণনা
সমস্ত সব বার্তা
ট্রেস সূক্ষ্ম দানাদার ডিবাগ বার্তা
ডিবাগ গুরুত্বপূর্ণ ডিবাগ বার্তা
তথ্য তথ্যমূলক বার্তা
সতর্ক করুন সতর্কতা
ত্রুটি ত্রুটি
মারাত্মক মারাত্মক ত্রুটি
বন্ধ কোন বার্তা নেই

বার্তাগুলি ফিল্টার করার সময়ও এই স্তরগুলি ব্যবহার করা হয়।

ধরুন আপনি লগিং লেভেল WARN এ সেট করেছেন। তারপরে সতর্কতার চেয়ে কম গুরুত্বপূর্ণ সমস্ত বার্তা বাতিল করা হবে: TRACE, DEBUG, INFO৷

আপনি যদি ফিল্টারিং লেভেলকে FATAL-এ সেট করেন, তাহলে এমনকি ERROR বার্তাগুলিও বাতিল করা হবে৷

"ফিল্টার করার সময় আরও দুটি গুরুত্বের স্তর ব্যবহার করা হয়: বন্ধ, যা সমস্ত বার্তা বাতিল করে; এবং সমস্ত, যা সমস্ত বার্তা দেখায় (কিছুই বাতিল করা হয় না)।"

"আমি কিভাবে এবং কোথায় ফিল্টারিং সেট আপ করব?"

"আমি আর কোন ঝামেলা ছাড়াই আপনাকে বলব।"

"সাধারণত, log4j লগার সেটিংস log4j.properties ফাইলে নির্দিষ্ট করা হয়।"

আপনি এই ফাইলে একাধিক অ্যাপেন্ডার অবজেক্ট নির্দিষ্ট করতে পারেন। এই বস্তুগুলিতে ডেটা লেখা হয়। তথ্য উৎস আছে, এবং পরিশিষ্ট আছে — বস্তুর বিপরীত উদ্দেশ্য আছে। বস্তু যে তথ্য জলের মত প্রবাহিত.

"এখানে কিছু উদাহরণঃ:"

কনসোলে লগিং করা হচ্ছে
# Root logger option
log4j.rootLogger = INFO, stdout

# Direct log messages to stdout
log4j.appender.stdout = org.apache.log4j.ConsoleAppender
log4j.appender.stdout.Target = System.out
log4j.appender.stdout.layout = org.apache.log4j.PatternLayout
log4j.appender.stdout.layout.ConversionPattern = %d{yyyy-MM-dd HH:mm:ss}

লাইন 1 এবং 4 - এই মন্তব্য

লাইন 2 - আমরা যে লগিং লেভেল চাই তা নির্দেশ করি। সমস্ত কম গুরুত্বপূর্ণ স্তর (DEBUG, TRACE) বাতিল করা হবে৷

একই জায়গায়, আমরা একটি কমা যোগ করি এবং তারপরে বস্তুর নামটি নির্দেশ করি (যা আমরা নিজেদের সাথে নিয়ে এসেছি) যে লগটি লেখা হবে। লাইন 5-9 এর সেটিংস ধারণ করে।

লাইন 5 - আমরা অ্যাপেন্ডারের ধরন নির্দিষ্ট করি ( কনসোলঅ্যাপেন্ডার )।

লাইন 6 - আমরা ঠিক কোথায় লিখছি তা আমরা নির্দেশ করি ( System.out. )।

লাইন 7 - আমরা ক্লাস সেট করি যা রূপান্তর প্যাটার্ন (প্যাটার্ন লেআউট) পরিচালনা করবে।

লাইন 8 - আমরা রূপান্তর প্যাটার্ন সেট করি যা লেখার জন্য ব্যবহার করা হবে। উপরের উদাহরণে, এটি তারিখ এবং সময়।

"এবং এখানে একটি ফাইলে লেখার মত দেখায়:"

একটি ফাইল লগিং
# Root logger option
log4j.rootLogger = INFO, file

# Direct log messages to a log file
log4j.appender.file = org.apache.log4j.RollingFileAppender
log4j.appender.file.File = C:\\loging.log
log4j.appender.file.MaxFileSize = 1MB
log4j.appender.file.MaxBackupIndex = 1
log4j.appender.file.layout = org.apache.log4j.PatternLayout
log4j.appender.file.layout.ConversionPattern = %-5p %c{1}:%L - %m%n

"লাইন 2 বার্তা ফিল্টারিং স্তর এবং অ্যাপেন্ডার অবজেক্টের নাম (সিঙ্ক) সেট করে।"

"লাইন 5 - আমরা ফাইল অ্যাপেন্ডার টাইপ ( RollingFileAppender ) নির্দিষ্ট করি।"

"লাইন 6 - আমরা ফাইলের নাম উল্লেখ করি যেটিতে লগ লেখা হবে।"

"লাইন 7 - আমরা সর্বোচ্চ লগ আকার নির্দিষ্ট করি। যখন এই আকারের সীমা অতিক্রম করা হয়, একটি নতুন ফাইল তৈরি করা হয়।"

"লাইন 8 - আমরা সংরক্ষণ করার জন্য পুরানো লগ ফাইলের সংখ্যা নির্দিষ্ট করি।"

"লাইন 9-10 - রূপান্তর প্যাটার্ন সেট করুন।"

"আমি জানি না এখানে কি ঘটছে, কিন্তু আমি অনুমান করতে পারি। এটা উৎসাহজনক।"

"এটি দুর্দান্ত। তারপরে একটি ফাইল এবং কনসোলে কীভাবে একটি লগ লিখতে হয় তার একটি উদাহরণ এখানে দেওয়া হল:"

কনসোল এবং একটি ফাইল লগিং
# Root logger option
log4j.rootLogger = INFO, file, stdout

# Direct log messages to a log file
log4j.appender.file = org.apache.log4j.RollingFileAppender
log4j.appender.file.File = C:\\loging.log
log4j.appender.file.MaxFileSize = 1MB
log4j.appender.file.MaxBackupIndex = 1
log4j.appender.file.layout = org.apache.log4j.PatternLayout
log4j.appender.file.layout.ConversionPattern = %-5p %c{1}:%L - %m%n

# Direct log messages to stdout
log4j.appender.stdout = org.apache.log4j.ConsoleAppender
log4j.appender.stdout.Target = System.out
log4j.appender.stdout.layout = org.apache.log4j.PatternLayout
log4j.appender.stdout.layout.ConversionPattern = %d{yyyy-MM-dd HH:mm:ss}

"আহ, তাই আপনি এটা করতে পারেন? এটা মহান!"

"হ্যাঁ। আপনি যতগুলো পরিশিষ্ট চান ঘোষণা করতে পারেন এবং প্রতিটিকে কাস্টমাইজ করতে পারেন।"

উপরন্তু, প্রতিটি অ্যাপেন্ডারে বার্তা ফিল্টারিংয়ের জন্য খুব নমনীয় সেটিংস থাকতে পারে। আমরা প্রতিটি অ্যাপেন্ডারে শুধুমাত্র একটি পৃথক বার্তা ফিল্টারিং স্তর নির্ধারণ করতে পারি না, তবে আমরা প্যাকেজ দ্বারা বার্তাগুলিও ফিল্টার করতে পারি! তাই লগার তৈরি করার সময় আপনাকে একটি ক্লাস নির্দিষ্ট করতে হবে (আমি LoggerFactory.getLogger সম্পর্কে বলছি )।

"উদাহরণ স্বরূপ:"

কনসোল এবং একটি ফাইল লগিং
# Root logger option
log4j.rootLogger = INFO, file, stdout

# Direct log messages to a log file
log4j.appender.file = org.apache.log4j.RollingFileAppender
log4j.appender.file.threshold = DEBUG
log4j.appender.file.File = C:\\loging.log
log4j.appender.file.MaxFileSize = 1MB
log4j.appender.file.MaxBackupIndex = 1
log4j.appender.file.layout=org.apache.log4j.PatternLayout
log4j.appender.file.layout.ConversionPattern = %-5p %c{1}:%L - %m%n

# Direct log messages to stdout
log4j.appender.stdout=org.apache.log4j.ConsoleAppender
log4j.appender.stdout.threshold = ERROR
log4j.appender.stdout.Target = System.out
log4j.appender.stdout.layout = org.apache.log4j.PatternLayout
log4j.appender.stdout.layout.ConversionPattern = %d{yyyy-MM-dd HH:mm:ss}

log4j.logger.org.springframework = ERROR
log4j.logger.org.hibernate = ERROR
log4j.logger.com.codegym = DEBUG
log4j.logger.org.apache.cxf = ERROR

"লাইন 6 এবং 15 - আমরা প্রতিটি অ্যাপেন্ডারের জন্য আমাদের নিজস্ব ফিল্টারিং স্তর সেট করি।"

"লাইন 20-23 - আমরা প্যাকেজের নাম এবং এর বার্তাগুলির জন্য ফিল্টারিং স্তর নির্দিষ্ট করি। Log4j.logger একটি উপসর্গ: প্যাকেজের নামটি কমলা রঙে হাইলাইট করা হয়েছে।"

"সত্যিই? তুমি এটাও করতে পারো। আচ্ছা, শান্ত!"

"যাইহোক, log4j বা slf4j উভয়ই JDK-তে অন্তর্ভুক্ত নয়। আপনাকে সেগুলি আলাদাভাবে ডাউনলোড করতে হবে। আপনি এটি এখানে করতে পারেন । কিন্তু আরেকটি উপায় আছে:"

" ধাপ 1 . ক্লাসে আমদানি যোগ করুন:"

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

" ধাপ 2। এই লাইনগুলিতে কার্সার রাখুন এবং IntelliJ IDEA-তে Alt+Enter চাপুন"

" ধাপ 3. 'ফাইল জার অন ওয়েব» মেনু আইটেমটি বেছে নিন।'

" ধাপ 4। 'slf4j-log4j13.jar' বেছে নিন"

" ধাপ 5। লাইব্রেরি (জার) কোথায় ডাউনলোড করতে হবে তা উল্লেখ করুন"

" ধাপ 6। আপনার প্রয়োজনীয় ক্লাসগুলি ব্যবহার করুন।"

"ওহ! এই কি একটি দিন ছিল. এত যে নতুন এবং অনেক যে শান্ত!"

"লগিংয়ের উপর এখানে আরেকটি ভাল নিবন্ধ রয়েছে: https://docs.oracle.com/javase/10/core/java-logging-overview.htm#JSCOR-GUID-48004124-2C00-49F7-A640-0C0DDA271DBC "

"ঠিক আছে, যথেষ্ট। প্রোগ্রামার, আরাম কর।"