flnews_post_proc 1.45 → 1.48

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: c48262d6fc3031346ffa1e2b528e11a696cef83b6d7c64fa98cdef444cf60247
4
- data.tar.gz: 12e53f1d88d613d14671ed06f03c0e65ca5f438088c85a66c22d3e37beec9b61
3
+ metadata.gz: 9a019c52dac602a5b00c71131e8b44a61769604a08035b7afad305a27c5d43a0
4
+ data.tar.gz: 7f5a69f62df2a18fefe9f0f5f499d7960d40b751b4bda67f26a88f91034ac941
5
5
  SHA512:
6
- metadata.gz: f1845950986bcb9919a4ad353c4913a9fca9427f2387bb8a4cbe7b1968eaf26f35d837f331dd9d3f9a1ab5c49b8e9a49d7868f89902c7b9f427d2592e73dc607
7
- data.tar.gz: f87ff6d5bd9462ebf3988b23482b64d6bb3d7ced99fbeecb06cc6c271392b65b7d8a510cd69e7e83c6792775ffbceb6e6dc1a6313b0bb2abd335752f508655ba
6
+ metadata.gz: fe1d5fee2fffc214f8aa96b34e4886b3c2e7b16a71dd2ac99b8df214528d53c43df8b425fe4b21d4edf58e691e6cd5f497e09ed12a81129dd0f0e883fcf9ab76
7
+ data.tar.gz: 40f0b45424e01cc6b034aeeb4a7729bb0a499e231eb0001a60d762e4f1952964090dacda102fb87215ed66786e7e2887c471c95cc930018b469df669d16915b1
data/README.md CHANGED
@@ -93,14 +93,14 @@ some users may not always agree with the result and for arbitrary reasons:
93
93
  Custom headers may be defined in the configuration file for the program
94
94
  and will then be added to each outgoing post.
95
95
 
96
- * The Archive- and X-No-Archive headers are sometimes set to avoid that an
97
- article be saved and stays available to search-engines (Google, notably).
98
- Test- postings, for example, do probably not justify at all that they would
99
- be referenced in search results. The post-processor program can impose the
100
- Archive- and X-No-Archive header for all posts to certain newsgroups.
101
-
102
- **ATTN** As of 2024, the X-No-Archive has lost most of its utility and it
103
- is the decision of server operators to honor it or not.
96
+ * The Archive- and X-No-Archive headers are sometimes set to avoid that an
97
+ article be saved and stays available to search-engines (Google, notably).
98
+ Test- postings, for example, do probably not justify at all that they would
99
+ be referenced in search results. The post-processor program can impose the
100
+ Archive- and X-No-Archive header for all posts to certain newsgroups.
101
+
102
+ **ATTN** As of 2024, the header “X-No-Archive has lost most of its utility
103
+ and it is the decision of server operators to honor it or not.
104
104
 
105
105
  * If a news post contains many references to either other posts or Web
106
106
  pages, the text can be cluttered with URLs.
data/bin/flnews_post_proc CHANGED
@@ -1,5 +1,6 @@
1
1
  #!/bin/env ruby
2
2
  #encoding: UTF-8
3
+
3
4
  =begin
4
5
  /***************************************************************************
5
6
  * ©2023-2024, Michael Uplawski <michael.uplawski@uplawski.eu> *
@@ -32,7 +33,6 @@ self.extend(BasicLogging)
32
33
 
33
34
  msg = PROGNAME.dup << ' ' << PROGVERSION << ' starting'
34
35
  msg = "–––––– " << msg << " ––––––"
35
-
36
36
  info msg
37
37
  # Get a configuration
38
38
  config = Configuration::instance
data/lib/basic_logging.rb CHANGED
@@ -48,26 +48,30 @@ module BasicLogging
48
48
 
49
49
  # set the log level
50
50
  def set_level(lv)
51
- if lv.respond_to?(:to_str)
51
+ if lv.respond_to?(:to_str) && Levels.keys.include?(lv.strip.to_sym)
52
52
  lv = Levels[lv.to_sym]
53
+ elsif lv.respond_to?(:to_sym) && Levels.keys.include?(lv)
54
+ lv = Levels[lv]
53
55
  end
54
56
 
55
57
  if(!lv || (lv.respond_to?(:to_int) && lv >= DEBUG && lv <= FATAL) )
56
58
  @@log_level = lv
57
59
  else
58
- STDERR.puts __FILE__.dup << ": ERROR : invalid log level \"" << lv.to_s << "\""
59
- STDERR.puts "Keepinng old log level " << Levels.keys.detect {| k| Levels[k] == @@log_level}.to_s
60
+ msg = __FILE__.dup << ": ERROR : invalid log level \"" << lv.to_s << "\""
61
+ msg << "\n" << "Keepinng old log level " << Levels.keys.detect {| k| Levels[k] == @@log_level}.to_s
62
+ STDERR.puts msg
63
+ puts msg
60
64
  end
61
65
  end
62
66
 
63
67
  # set the log target
64
68
  def set_target(tg)
65
- if !tg || tg.strip.empty?
66
- @@target = nil
67
- elsif tg.respond_to?(:to_io)
69
+ if tg.respond_to?(:to_io)
68
70
  @@target = tg
69
71
  elsif(!File::exist?(tg) || ( File.file?(tg) && File.writable?(tg) ) )
70
72
  @@target = File.open(tg, 'w+')
73
+ elsif !tg || tg.respond_to?(:to_str) && tg.strip.empty?
74
+ @@target = nil
71
75
  else
72
76
  STDERR.puts __FILE__.dup << ': ERROR : target ' << tg << ' cannot be set'
73
77
  STDERR.puts "Keeping old target " << @@target.inspect
@@ -91,22 +95,50 @@ module BasicLogging
91
95
  end
92
96
  end
93
97
 
98
+ def target
99
+ @@target.path if @@target
100
+ end
101
+
102
+ def level
103
+ @@level.to_s if @@level
104
+ end
105
+
106
+ # Clear the log (-file)
107
+ def clear_log
108
+ if @@target && @@target.respond_to?(:truncate)
109
+ lock_target{ @@target.truncate(0) }
110
+ end
111
+ end
112
+
94
113
  alias :debug :log
95
114
  alias :info :log
96
115
  alias :warn :log
97
116
  alias :error :log
98
117
  alias :fatal :log
99
118
 
100
- attr_reader :target, :log_level
101
119
 
102
120
  private
103
121
 
122
+ def lock_target(&block)
123
+ begin
124
+ if @@target.respond_to?(:flock)
125
+ @@target.flock(File::LOCK_EX)
126
+ block.call
127
+ @@target.flock(File::LOCK_UN)
128
+ elsif @@target.respond_to?(:to_io)
129
+ block.call
130
+ end
131
+ rescue => ex
132
+ STDERR.puts __FILE__.dup << ": ERROR : cannot lock target (" << ex.message << ")"
133
+ end
134
+ end
135
+
104
136
  # 1 format_log for all loggers.
105
137
  def format_log(message, mlevel)
106
138
  if @@target
107
139
  # indicate if a registered class or the registered object of a class is calling.
108
140
  name = self.class == Class ? self.name.dup << ' [class]' : self.class.name
109
- @@target.puts '' << name << ' ' << mlevel.to_s << ' ' << Time.now.strftime("%H:%M:%S:%6N") << ': ' << message.gsub("\n", "\n |")
141
+ lock_target{@@target.puts '' << name << ' ' << mlevel.to_s << ' ' << Time.now.strftime("%H:%M:%S:%6N") << ': ' << message.gsub("\n", "\n |")}
110
142
  end
111
143
  end
112
144
  end
data/lib/body.rb CHANGED
@@ -87,7 +87,7 @@ class Body
87
87
  i = i.next
88
88
  line = @lines[i]
89
89
  end
90
- # check if there is a citation, at all
90
+ # check if there is a quote, at all
91
91
  if(line.start_with?('>'))
92
92
  debug("\tfound intro " << ointro)
93
93
  # variables are part of the $intro.
@@ -119,9 +119,13 @@ class Body
119
119
  end
120
120
 
121
121
  def join
122
- return @lines.join("\r\n")
122
+ return @lines.join("\r\n") << "\r\n"
123
123
  end
124
-
124
+ # ------->
125
+ # TODO : Concentrate all URL/URI munging functionality in 1 or 2 helper
126
+ # classes, e.g. Body::News and Body::Http
127
+ # <------
128
+
125
129
  # Verify and possibly correct links in the post.
126
130
  # Simple.
127
131
  def handle_urls()
data/lib/configuration.rb CHANGED
@@ -25,7 +25,6 @@ class Configuration
25
25
  include Singleton
26
26
  include BasicLogging
27
27
 
28
- self.extend(BasicLogging)
29
28
 
30
29
  def initialize()
31
30
  debug 'Configuration::initialize()'
@@ -115,12 +114,16 @@ class Configuration
115
114
  if File::exist?(@config_file) && File::readable?(@config_file)
116
115
  begin
117
116
  @conf = YAML::load_file(@config_file)
117
+
118
118
  @conf.transform_keys!{|k| k.to_sym}
119
119
  @keys = @conf.keys
120
120
  clevel = @conf[:LOG_LEVEL]
121
121
  set_level clevel
122
- set_target @conf[:DEBUG_LOG]
123
- debug('log target and -level set: ' << @@log_level.to_s << ', ' << @@target.path)
122
+ target_string = @conf[:DEBUG_LOG]
123
+ set_target (target_string == 'STDOUT' ? STDOUT : target_string)
124
+ # clear the log file.
125
+ clear_log
126
+ debug('log target and -level set: ' << @@log_level.to_s << ', ' << target_string)
124
127
  rescue Exception => ex
125
128
  msg = ex.message
126
129
  error msg
@@ -29,11 +29,10 @@ $LN = "\r\n"
29
29
  # The main application class.
30
30
  # Does it.
31
31
  class PostProcessor
32
- # class-level configuration object
33
- @@config = Configuration.instance
34
32
  include BasicLogging
35
33
 
36
34
  def initialize(article_text)
35
+ @config = Configuration.instance
37
36
  # for simplicity.
38
37
  # separate the headers and the body.
39
38
  debug ' initializing headers'
data/lib/headers.rb CHANGED
@@ -20,13 +20,12 @@ require_relative 'newsgroups'
20
20
  # an object of this class represents the headers of a news-article
21
21
 
22
22
  class Headers
23
- # class-level configuration object
24
- @@config = Configuration.instance
25
23
  include BasicLogging
26
24
 
27
25
  # read the headers from the article
28
26
  def initialize(article_text)
29
27
 
28
+ @config = Configuration.instance
30
29
  line = nil
31
30
  # transform the article to an array.
32
31
  debug('before split, article_text is : ' << article_text)
@@ -105,10 +104,10 @@ class Headers
105
104
  @headers["X-No-Archive".to_sym] = no_archive
106
105
  @headers["Archive".to_sym] = 'no'
107
106
  end
108
- if @@config.CUSTOM_HEADERS
109
- ch = @@config.CUSTOM_HEADERS
107
+ if @config.CUSTOM_HEADERS
108
+ ch = @config.CUSTOM_HEADERS
110
109
  debug('setting custom headers : ' << ch.inspect)
111
- @@config.CUSTOM_HEADERS.each do |pair|
110
+ @config.CUSTOM_HEADERS.each do |pair|
112
111
  ch = pair.split(':')
113
112
  hn = ch[0].strip
114
113
  hv = ch[1].strip
data/lib/newsgroups.rb CHANGED
@@ -20,11 +20,10 @@ require_relative 'configuration'
20
20
  require_relative 'basic_logging'
21
21
 
22
22
  class Newsgroups
23
- # class-level configuration object
24
- @@config = Configuration.instance
25
- include BasicLogging
26
23
 
24
+ include BasicLogging
27
25
  def initialize(groups)
26
+ @config = Configuration.instance
28
27
  @groups = groups.split(',')
29
28
  debug('set signature, intro, no_archive')
30
29
  # set details for this post
@@ -50,7 +49,7 @@ class Newsgroups
50
49
  # only one group.
51
50
  group = @groups[0]
52
51
  # all configured intro-lines.
53
- gintros = @@config.GROUP_INTROS
52
+ gintros = @config.GROUP_INTROS
54
53
 
55
54
  if gintros && gintros.respond_to?(:to_hash)
56
55
  # find the intro for the group.
@@ -93,7 +92,7 @@ class Newsgroups
93
92
  @signature = nil
94
93
  # 1 group
95
94
  group = @groups[0]
96
- gsigs = @@config.GROUP_SIGS
95
+ gsigs = @config.GROUP_SIGS
97
96
 
98
97
  if gsigs && gsigs.respond_to?(:to_hash)
99
98
  # find the signature for the group
@@ -124,7 +123,7 @@ class Newsgroups
124
123
  # define the no_archive header.
125
124
  def set_no_archive
126
125
  @no_archive = nil
127
- xgs = @@config.NO_ARCHIVE_GROUPS
126
+ xgs = @config.NO_ARCHIVE_GROUPS
128
127
  if xgs && !xgs.empty? && xgs.detect {|g| @groups[0].match(g) }
129
128
  debug("setting no_archive")
130
129
  @no_archive = 'yes'
data/lib/version.rb CHANGED
@@ -14,8 +14,9 @@
14
14
  =end
15
15
 
16
16
  PROGNAME = 'flnews_post_proc'
17
- PROGVERSION = "1.45"
17
+ PROGVERSION = "1.48"
18
18
  AUTHORS = "Michael Uplawski"
19
19
  EMAIL = "michael.uplawski@uplawski.eu"
20
20
  YEARS = "2023 - 2024"
21
- SUMMARY = "Bugfix: URLs exclude punctuation and others at the end."
21
+ SUMMARY = "\tConcurrent access to the log file\n\tLog cleared upon setting log target"
22
+ SUMMARY << "\n\t\"STDOUT\" allowed as log target"
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: flnews_post_proc
3
3
  version: !ruby/object:Gem::Version
4
- version: '1.45'
4
+ version: '1.48'
5
5
  platform: ruby
6
6
  authors:
7
7
  - Michael Uplawski
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2024-05-11 00:00:00.000000000 Z
11
+ date: 2024-05-30 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: diffy
@@ -82,8 +82,9 @@ required_rubygems_version: !ruby/object:Gem::Requirement
82
82
  - !ruby/object:Gem::Version
83
83
  version: '0'
84
84
  requirements: []
85
- rubygems_version: 3.4.20
85
+ rubygems_version: 3.5.3
86
86
  signing_key:
87
87
  specification_version: 4
88
- summary: 'Bugfix: URLs exclude punctuation and others at the end.'
88
+ summary: Concurrent access to the log file Log cleared upon setting log target "STDOUT"
89
+ allowed as log target
89
90
  test_files: []