blackstack-core 1.2.27 → 1.2.29

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (3) hide show
  1. checksums.yaml +4 -4
  2. data/lib/functions.rb +194 -167
  3. metadata +2 -2
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 51ccdc5a340ef6ea723f5a4698b915fbb0502c8ee787f493738993ceedd174d1
4
- data.tar.gz: 3918dd18149cd98f2aea89a2809e388b419a4a574735c5556d213555518f8c19
3
+ metadata.gz: 61e89c40560e966edd297c6fbce7e0099a94bce4dd88c0653f7e20feceb8234e
4
+ data.tar.gz: 28543d06207cc6399371e857b0982ec7432801e5344372304165a0aaa4053660
5
5
  SHA512:
6
- metadata.gz: 7cbec53ec3c0c135c9d241677bb85d9375fd0cd03b7b8c5d410d598cdc956d79195b43a9930f3919170352cd7fb2248d8e1e35283e5e8776102be6a9c41e570f
7
- data.tar.gz: 38f3be7efc93d053acc74f3b927caa4b87a53d3f05718c49526301ad8d1b984a6b3a9960e6f4f3d1f4ea14d71b073e06d3d40aa93d93bc36113b8b0e116d5f1c
6
+ metadata.gz: 8545ef59846393d06cb272b8e503847b3c11e9837933ac770c546acf724265a6e560407dea7bcbe67bccf49ec505b89463b4aab52bb83094fdeb792b517f7479
7
+ data.tar.gz: 3eaac8af64b460a4cf941d3756faa219da65a75300cbe47fe1574ae4bb9426e3a5d6a2c028dcb81e940646bc4566f433ed48493cbf4665c5eee58d76b341823f
data/lib/functions.rb CHANGED
@@ -20,7 +20,7 @@ module BlackStack
20
20
 
21
21
  def self.api_url
22
22
  @@api_url
23
- end
23
+ end
24
24
 
25
25
  def self.api_port
26
26
  @@api_port
@@ -34,14 +34,10 @@ module BlackStack
34
34
  @@backtrace
35
35
  end # def self.backtrace
36
36
 
37
- def self.api_url()
38
- "#{BlackStack::API.api_protocol}://#{BlackStack::API.api_domain}:#{BlackStack::API.api_port}"
39
- end
40
-
41
37
  def self.classes
42
38
  @@classes
43
39
  end # def self.classes
44
-
40
+
45
41
  def self.set_client(
46
42
  api_key: ,
47
43
  api_url: ,
@@ -64,7 +60,7 @@ module BlackStack
64
60
  end # def self.set_server
65
61
 
66
62
  def self.post(
67
- endpoint: ,
63
+ endpoint: ,
68
64
  params: {}
69
65
  )
70
66
  begin
@@ -88,7 +84,7 @@ module BlackStack
88
84
 
89
85
  # Base class.
90
86
  # List of methods you have to overload if you develop a profile type.
91
- #
87
+ #
92
88
  class Base
93
89
  # object json descriptor
94
90
  attr_accessor :desc
@@ -124,10 +120,10 @@ module BlackStack
124
120
 
125
121
 
126
122
  # Get array of hash descriptor of profile.
127
- #
128
- # Parameters:
123
+ #
124
+ # Parameters:
129
125
  # - id_account: guid. Id of the account to bring the profiles. Sysowner must provide the id_account for getting an account value. For non sysowner it is assigned to his account.
130
- # - promiscuous: boolean. It works only for Sysowner. If true, it will bring all non-deleted rows. If false, it will bring only rows matching id_profile. Default: false.
126
+ # - promiscuous: boolean. It works only for Sysowner. If true, it will bring all non-deleted rows, including the ones that are not owned by Sysowner. If false, it will bring only rows matching id_profile. Default: false.
131
127
  # - page: integer. Page number.
132
128
  # - limit: integer. Number of profiles per page.
133
129
  # - params: hash. Additional filter parameters used by the specific child class.
@@ -151,8 +147,8 @@ module BlackStack
151
147
  end # def self.base
152
148
 
153
149
  # Get array of hash descriptors of profiles.
154
- #
155
- # Parameters:
150
+ #
151
+ # Parameters:
156
152
  # - id: guid. Id of the profile to bring.
157
153
  #
158
154
  def self.count
@@ -167,8 +163,8 @@ module BlackStack
167
163
  end # def self.count
168
164
 
169
165
  # Get array of hash descriptors of profiles.
170
- #
171
- # Parameters:
166
+ #
167
+ # Parameters:
172
168
  # - id: guid. Id of the profile to bring.
173
169
  #
174
170
  def self.get(id)
@@ -183,6 +179,23 @@ module BlackStack
183
179
  return self.new(ret['result']).child_class_instance
184
180
  end # def self.get
185
181
 
182
+ # Delete object.
183
+ #
184
+ # Parameters:
185
+ # - id: guid. Id of the profile to bring.
186
+ #
187
+ def self.delete(id)
188
+ params = {}
189
+ params['id'] = id
190
+ params['backtrace'] = BlackStack::API.backtrace
191
+ ret = BlackStack::API.post(
192
+ endpoint: "#{self.object_name}/delete",
193
+ params: params
194
+ )
195
+ raise "Error calling get endpoint: #{ret['status']}" if ret['status'] != 'success'
196
+ return self.new(ret['result']).child_class_instance
197
+ end # def self.get
198
+
186
199
  # Submit a hash descriptor to the server for an update
187
200
  #
188
201
  def self.update(desc)
@@ -252,6 +265,20 @@ module BlackStack
252
265
  return ret['result'] == {} ? nil : self.new(ret['result']).child_class_instance
253
266
  end # def self.upsert
254
267
 
268
+ # Submit a hash descriptor to the server for an upsert
269
+ #
270
+ def self.upsert2(desc)
271
+ params = {}
272
+ params['desc'] = desc
273
+ params['backtrace'] = BlackStack::API.backtrace
274
+ ret = BlackStack::API.post(
275
+ endpoint: "#{self.object_name}/upsert2",
276
+ params: params
277
+ )
278
+ raise "Error calling upsert endpoint: #{ret['status']}" if ret['status'] != 'success'
279
+ return ret['result'] == {} ? nil : self.new(ret['result']).child_class_instance
280
+ end # def self.upsert
281
+
255
282
  # Submit a hash descriptor to the server for an upsert
256
283
  #
257
284
  def upsert
@@ -270,7 +297,7 @@ module BlackStack
270
297
  ret = nil
271
298
  # getting the HTML
272
299
  zyte = ZyteClient.new(key: api_key)
273
- html = zyte.extract(url: url, options: options, data_filename: data_filename)
300
+ html = zyte.extract(url: url, options: options, data_filename: data_filename)
274
301
  # return the URL of the file in the cloud
275
302
  return html
276
303
  end # def zyte_html
@@ -288,7 +315,7 @@ module BlackStack
288
315
  def zyte_snapshot(url, api_key:, options:, data_filename:, dropbox_folder:nil, retry_times: 3)
289
316
  # "The garbage character must be due to the 520 error code which was caused on the second request."
290
317
  garbage = "\x9E\xE9e"
291
-
318
+
292
319
  ret = nil
293
320
  raise "Either dropbox_folder parameter or self.desc['id_account'] are required." if dropbox_folder.nil? && self.desc['id_account'].nil?
294
321
  dropbox_folder = self.desc['id_account'] if dropbox_folder.nil?
@@ -306,7 +333,7 @@ module BlackStack
306
333
  try = 0
307
334
  html = garbage
308
335
  while try < retry_times && html == garbage
309
- html = zyte.extract(url: url, options: options, data_filename: data_filename)
336
+ html = zyte.extract(url: url, options: options, data_filename: data_filename)
310
337
  try += 1
311
338
  end
312
339
  # save the HTML in the local file in /tmp
@@ -322,9 +349,9 @@ module BlackStack
322
349
 
323
350
  end # class Base
324
351
 
325
- # -----------------------------------------------------------------------------------------
352
+ # -----------------------------------------------------------------------------------------
326
353
  # PRY Supporting Functions
327
- # -----------------------------------------------------------------------------------------
354
+ # -----------------------------------------------------------------------------------------
328
355
  module Debugging
329
356
  @@allow_breakpoints = false
330
357
  @@verbose = false
@@ -345,7 +372,7 @@ module BlackStack
345
372
  print "Breakpoint are not allowed" if @@verbose
346
373
  end
347
374
 
348
- Binding.class_eval do
375
+ Binding.class_eval do
349
376
  alias_method :old_pry, :pry
350
377
  define_method :pry, new_pry
351
378
  end
@@ -353,21 +380,21 @@ module BlackStack
353
380
  end
354
381
  end
355
382
 
356
- # -----------------------------------------------------------------------------------------
383
+ # -----------------------------------------------------------------------------------------
357
384
  # OCRA Supporting Functions
358
- # -----------------------------------------------------------------------------------------
385
+ # -----------------------------------------------------------------------------------------
359
386
  module OCRA
360
387
  # OCRA files run into a temp folder, where the script is unpacked.
361
- #
388
+ #
362
389
  # This function is useful to require a configuration file when the
363
390
  # script is running inside an OCRA temp folder, since the local folder
364
391
  # of the running command is not the filder where the exe file is hosted.
365
- #
366
- # More information:
392
+ #
393
+ # More information:
367
394
  # * https://stackoverflow.com/questions/1937743/how-to-get-the-current-working-directorys-absolute-path-from-irb
368
395
  # * https://stackoverflow.com/questions/8577223/ruby-get-the-file-being-executed
369
396
  # * https://stackoverflow.com/questions/7399882/ruby-getting-path-from-pathfilename/7400057
370
- #
397
+ #
371
398
  def self.require_in_working_path(filename, path, show_path_info=false)
372
399
  puts '' if show_path_info
373
400
  path = File.expand_path File.dirname(path)
@@ -379,13 +406,13 @@ module BlackStack
379
406
  end
380
407
  end # module OCRA
381
408
 
382
- # -----------------------------------------------------------------------------------------
409
+ # -----------------------------------------------------------------------------------------
383
410
  # DateTime Functions
384
- # -----------------------------------------------------------------------------------------
385
- module DateTime
386
- # -----------------------------------------------------------------------------------------
411
+ # -----------------------------------------------------------------------------------------
412
+ module DateTime
413
+ # -----------------------------------------------------------------------------------------
387
414
  # Encoding
388
- # -----------------------------------------------------------------------------------------
415
+ # -----------------------------------------------------------------------------------------
389
416
  module Encoding
390
417
  # Convierte un objeto date-time a un string con formato sql-datetime (yyyy-mm-dd hh:mm:ss).
391
418
  def self.datetime_to_sql(o)
@@ -393,50 +420,50 @@ module BlackStack
393
420
  end
394
421
  end # module Encode
395
422
 
396
- # -----------------------------------------------------------------------------------------
423
+ # -----------------------------------------------------------------------------------------
397
424
  # Miscelaneous
398
- # -----------------------------------------------------------------------------------------
425
+ # -----------------------------------------------------------------------------------------
399
426
  module Misc
400
427
  def self.datetime_values_check(year,month,day,hour,minute,second)
401
428
  if (year.to_i<1900 || year.to_i>=2100)
402
429
  return false
403
430
  end
404
-
431
+
405
432
  if (month.to_i<1 || month.to_i>12)
406
433
  return false
407
434
  end
408
-
435
+
409
436
  # TODO: Considerar la cantidad de dias de cada mes, y los anios biciestos. Buscar alguna funcion existente.
410
437
  if (day.to_i<1 || day.to_i>31)
411
438
  return false
412
439
  end
413
-
440
+
414
441
  if (hour.to_i<0 || hour.to_i>23)
415
442
  return false
416
443
  end
417
-
444
+
418
445
  if (minute.to_i<0 || minute.to_i>59)
419
446
  return false
420
447
  end
421
-
448
+
422
449
  if (second.to_i<0 || second.to_i>59)
423
450
  return false
424
451
  end
425
-
452
+
426
453
  return true
427
454
  end # datetime_values_check
428
455
  end # module Misc
429
456
  end # module DateTime
430
457
 
431
- # -----------------------------------------------------------------------------------------
458
+ # -----------------------------------------------------------------------------------------
432
459
  # Numeric Functions
433
- # -----------------------------------------------------------------------------------------
460
+ # -----------------------------------------------------------------------------------------
434
461
  module Number
435
- # -----------------------------------------------------------------------------------------
462
+ # -----------------------------------------------------------------------------------------
436
463
  # Encoding
437
- # -----------------------------------------------------------------------------------------
464
+ # -----------------------------------------------------------------------------------------
438
465
  module Encoding
439
- # Converts number to a string with a format like xx,xxx,xxx.xxxx
466
+ # Converts number to a string with a format like xx,xxx,xxx.xxxx
440
467
  # number: it may be int or float
441
468
  def self.format_with_separator(number)
442
469
  whole_part, decimal_part = number.to_s.split('.')
@@ -448,7 +475,7 @@ module BlackStack
448
475
  # Ejemplo: "4 hours, 30 minutes"
449
476
  # Ejemplo: "3 days, 4 hour"
450
477
  def self.encode_minutes(n)
451
- # TODO: validar que n sea un entero mayor a 0
478
+ # TODO: validar que n sea un entero mayor a 0
452
479
  if (n<0)
453
480
  return "?"
454
481
  end
@@ -463,13 +490,13 @@ module BlackStack
463
490
  end # module Encode
464
491
  end # module Number
465
492
 
466
- # -----------------------------------------------------------------------------------------
493
+ # -----------------------------------------------------------------------------------------
467
494
  # String Functions
468
- # -----------------------------------------------------------------------------------------
495
+ # -----------------------------------------------------------------------------------------
469
496
  module Strings
470
497
 
471
498
  GUID_SIZE = 36
472
- MATCH_PASSWORD = /(?=.*[a-zA-Z])(?=.*[0-9]).{6,}/
499
+ MATCH_PASSWORD = /(?=.*[a-zA-Z])(?=.*[0-9]).{6,}/
473
500
  MATCH_GUID = /{?[0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F]\-[0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F]\-[0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F]-[0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F]\-[0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F][0-9a-fA-F]}?/
474
501
  MATCH_FILENAME = /[\w\-\_\.]+/
475
502
  MATCH_EMAIL = /[A-Z0-9._%a-z\-]+@(?:[A-Z0-9a-z\-]+\.)+[A-Za-z]{1,25}/
@@ -478,7 +505,7 @@ module BlackStack
478
505
  MATCH_PHONE = /(?:\+\d{1,2}\s)?\(?\d{3}\)?[\s.-]?\d{3}[\s.-]?\d{4}/
479
506
 
480
507
  # Note: MATCH_URL gets the URL up to '?', but it doesn't retrieves the parameters.
481
- # Exmaple:
508
+ # Exmaple:
482
509
  # https://foo.com/bar?param1=value1&param2=value2 --> https://foo.com/bar?
483
510
  # https://foo.com/bar/?param1=value1&param2=value2 --> https://foo.com/bar/?
484
511
  MATCH_URL = /(https?:\/\/)?([\da-z\.-]+)([\.\:])([\da-z]{2,6})([\/[\da-z\.\-]+]*[\da-z])(\/)?(\?)?/i
@@ -488,32 +515,32 @@ module BlackStack
488
515
  MATCH_CONTENT_SPINNING = /{[^}]+}/
489
516
  MATCH_SPINNED_TEXT = /code me/ # TODO: define this regex for the issue #1226
490
517
 
491
- # -----------------------------------------------------------------------------------------
518
+ # -----------------------------------------------------------------------------------------
492
519
  # Fuzzy String Comparsion Functions: How similar are 2 strings that are not exactly equal.
493
- # -----------------------------------------------------------------------------------------
520
+ # -----------------------------------------------------------------------------------------
494
521
  module SQL
495
522
  def self.string_to_sql_string(s)
496
523
  #return s.force_encoding("UTF-8").gsub("'", "''").to_s
497
524
  return s.gsub("'", "''").to_s
498
525
  end
499
526
  end
500
-
501
- # -----------------------------------------------------------------------------------------
527
+
528
+ # -----------------------------------------------------------------------------------------
502
529
  # Fuzzy String Comparsion Functions: How similar are 2 strings that are not exactly equal.
503
- # -----------------------------------------------------------------------------------------
530
+ # -----------------------------------------------------------------------------------------
504
531
  module Comparing
505
532
  # retorna 0 si los strings son iguales
506
533
  # https://stackoverflow.com/questions/16323571/measure-the-distance-between-two-strings-with-ruby
507
- def self.levenshtein_distance(s, t)
534
+ def self.levenshtein_distance(s, t)
508
535
  s.downcase!
509
536
  t.downcase!
510
-
537
+
511
538
  m = s.length
512
539
  n = t.length
513
540
  return m if n == 0
514
541
  return n if m == 0
515
542
  d = Array.new(m+1) {Array.new(n+1)}
516
-
543
+
517
544
  (0..m).each {|i| d[i][0] = i}
518
545
  (0..n).each {|j| d[0][j] = j}
519
546
  (1..n).each do |j|
@@ -530,7 +557,7 @@ module BlackStack
530
557
  end
531
558
  d[m][n]
532
559
  end
533
-
560
+
534
561
  # retorna la cantidad de palabras con mas de 3 caracteres que se encuentran en el parametro s
535
562
  def self.max_sardi_distance(s)
536
563
  s.downcase!
@@ -545,14 +572,14 @@ module BlackStack
545
572
  }
546
573
  n
547
574
  end
548
-
575
+
549
576
  # retorna la cantidad de palabras con mas de 3 caracteres del parametro s que se encuentran en el parametro t
550
577
  def self.sardi_distance(s, t)
551
578
  s.downcase!
552
579
  t.downcase!
553
580
  s.gsub!(/-/,' ')
554
581
  t.gsub!(/-/,' ')
555
- max_distance = max_sardi_distance(s)
582
+ max_distance = max_sardi_distance(s)
556
583
  ss = s.scan(/\b([a-z]+)\b/)
557
584
  tt = t.scan(/\b([a-z]+)\b/)
558
585
  n = 0
@@ -567,20 +594,20 @@ module BlackStack
567
594
  return max_distance - n
568
595
  end
569
596
  end # module Comparing
570
-
571
- # -----------------------------------------------------------------------------------------
597
+
598
+ # -----------------------------------------------------------------------------------------
572
599
  # Encoding: Make a string nice to be shown into an HTML string.
573
- # -----------------------------------------------------------------------------------------
600
+ # -----------------------------------------------------------------------------------------
574
601
  module Encoding
575
602
  # Then it makes it compatible with UTF-8.
576
- # More details here: https://bitbucket.org/leandro_sardi/blackstack/issues/961
603
+ # More details here: https://bitbucket.org/leandro_sardi/blackstack/issues/961
577
604
  def self.encode_string(s)
578
605
  s.encode("UTF-8")
579
606
  end
580
-
607
+
581
608
  # Escape the string to be shown into an HTML screen.
582
609
  # Then it makes it compatible with UTF-8.
583
- # More details here: https://bitbucket.org/leandro_sardi/blackstack/issues/961
610
+ # More details here: https://bitbucket.org/leandro_sardi/blackstack/issues/961
584
611
  def self.encode_html(s)
585
612
  encode_string(CGI.escapeHTML(s.to_s))
586
613
  end
@@ -588,9 +615,9 @@ module BlackStack
588
615
  # Generates a description string from an exception object.
589
616
  # Eescapes the string to be shown into an HTML screen.
590
617
  # Makes it compatible with UTF-8.
591
- # More details here: https://bitbucket.org/leandro_sardi/blackstack/issues/961
618
+ # More details here: https://bitbucket.org/leandro_sardi/blackstack/issues/961
592
619
  def self.encode_exception(e, include_backtrace=true)
593
- ret = encode_html(e.to_s)
620
+ ret = encode_html(e.to_s)
594
621
  if (include_backtrace == true)
595
622
  e.backtrace.each { |s|
596
623
  ret += "<br/>" + encode_html(s)
@@ -600,8 +627,8 @@ module BlackStack
600
627
  end
601
628
 
602
629
  # Returns a string with a description of a period of time, to be shown in the screen.
603
- # period: it may be 'H', 'D', 'W', 'M', 'Y'
604
- # units: it is a positive integer
630
+ # period: it may be 'H', 'D', 'W', 'M', 'Y'
631
+ # units: it is a positive integer
605
632
  def self.encode_period(period, units)
606
633
  s = "Last "
607
634
  s += units.to_i.to_s + " " if units.to_i > 1
@@ -630,87 +657,87 @@ module BlackStack
630
657
 
631
658
  end # module Encoding
632
659
 
633
- # -----------------------------------------------------------------------------------------
660
+ # -----------------------------------------------------------------------------------------
634
661
  # DateTime
635
- # -----------------------------------------------------------------------------------------
636
- module DateTime
662
+ # -----------------------------------------------------------------------------------------
663
+ module DateTime
637
664
  # Check the string has the format yyyymmddhhmmss.
638
665
  # => Return true if success. Otherwise, return false.
639
666
  # => Year cannot be lower than 1900.
640
- # => Year cannot be higher or equal than 2100.
667
+ # => Year cannot be higher or equal than 2100.
641
668
  def self.datetime_api_check(s)
642
- return false if (s.size!=14)
669
+ return false if (s.size!=14)
643
670
  year = s[0..3]
644
671
  month = s[4..5]
645
- day = s[6..7]
646
- hour = s[8..9]
647
- minute = s[10..11]
648
- second = s[12..13]
672
+ day = s[6..7]
673
+ hour = s[8..9]
674
+ minute = s[10..11]
675
+ second = s[12..13]
649
676
  BlackStack::DateTime::Misc::datetime_values_check(year,month,day,hour,minute,second)
650
677
  end # def datetime_api_check
651
678
 
652
679
  # Check the string has the format yyyy-mm-dd hh:mm:ss.
653
680
  # => Return true if success. Otherwise, return false.
654
681
  # => Year cannot be lower than 1900.
655
- # => Year cannot be higher or equal than 2100.
682
+ # => Year cannot be higher or equal than 2100.
656
683
  def self.datetime_sql_check(s)
657
684
  return false if (s.size!=19)
658
685
  year = s[0..3]
659
686
  month = s[5..6]
660
- day = s[8..9]
661
- hour = s[11..12]
662
- minute = s[14..15]
663
- second = s[17..18]
687
+ day = s[8..9]
688
+ hour = s[11..12]
689
+ minute = s[14..15]
690
+ second = s[17..18]
664
691
  BlackStack::DateTime::Misc::datetime_values_check(year,month,day,hour,minute,second)
665
692
  end # def datetime_sql_check
666
-
693
+
667
694
  # Convierte un string con formato api-datatime (yyyymmddhhmmss) a un string con formato sql-datetime (yyyy-mm-dd hh:mm:ss).
668
695
  def self.datetime_api_to_sql(s)
669
696
  raise "Wrong Api DataTime Format." if (datetime_api_check(s)==false)
670
697
  year = s[0..3]
671
698
  month = s[4..5]
672
- day = s[6..7]
673
- hour = s[8..9]
674
- minute = s[10..11]
675
- second = s[12..13]
676
- ret = "#{year}-#{month}-#{day} #{hour}:#{minute}:#{second}"
699
+ day = s[6..7]
700
+ hour = s[8..9]
701
+ minute = s[10..11]
702
+ second = s[12..13]
703
+ ret = "#{year}-#{month}-#{day} #{hour}:#{minute}:#{second}"
677
704
  return ret
678
- end # def datetime_api_to_sql
679
-
705
+ end # def datetime_api_to_sql
706
+
680
707
  # Convierte un string con formato sql-datatime a un string con formato sql-datetime.
681
708
  def self.datetime_sql_to_api(s)
682
709
  raise "Wrong SQL DataTime Format." if (datetime_sql_check(s)==false)
683
710
  year = s[0..3]
684
711
  month = s[5..6]
685
- day = s[8..9]
686
- hour = s[11..12]
687
- minute = s[14..15]
688
- second = s[17..18]
689
- ret = "#{year}#{month}#{day}#{hour}#{minute}#{second}"
712
+ day = s[8..9]
713
+ hour = s[11..12]
714
+ minute = s[14..15]
715
+ second = s[17..18]
716
+ ret = "#{year}#{month}#{day}#{hour}#{minute}#{second}"
690
717
  return ret
691
718
  end # def datetime_sql_to_api
692
719
  end # module DateTime
693
720
 
694
721
 
695
- # -----------------------------------------------------------------------------------------
722
+ # -----------------------------------------------------------------------------------------
696
723
  # Spinning
697
- # -----------------------------------------------------------------------------------------
724
+ # -----------------------------------------------------------------------------------------
698
725
  module Spinning
699
726
  # Esta funcion retorna una variacion al azar del texto que se pasa.
700
727
  # Esta funcion se ocupa de dividir el texto en partes, para eviar el error "too big to product" que arroja la libraría.
701
728
  def self.random_spinning_variation(text)
702
729
  ret = text
703
-
730
+
704
731
  text.scan(MATCH_CONTENT_SPINNING).each { |s|
705
732
  a = ContentSpinning.new(s).spin
706
733
  rep = a[rand(a.size)]
707
734
  ret = ret.gsub(s, rep)
708
735
  a = nil
709
736
  }
710
-
737
+
711
738
  return ret
712
739
  end
713
-
740
+
714
741
  # retorna true si la sintaxis del texto spineado es correcta
715
742
  # caso contrario retorna false
716
743
  # no soporta spinnings anidados. ejemplo: {my|our|{a car of mine}}
@@ -718,16 +745,16 @@ module BlackStack
718
745
  # valido que exste
719
746
  n = 0
720
747
  s.split('').each { |c|
721
- n+=1 if c=='{'
748
+ n+=1 if c=='{'
722
749
  n-=1 if c=='}'
723
750
  if n!=0 && n!=1
724
751
  #raise "Closing spining char '}' with not previous opening spining char '{'." if n<0
725
752
  #raise "Opening spining char '{' inside another spining block." if n>1
726
753
  return false if n<0 # Closing spining char '}' with not previous opening spining char '{'.
727
754
  return false if n>1 # Opening spining char '{' inside another spining block.
728
- end
755
+ end
729
756
  }
730
-
757
+
731
758
  return false if n!=0
732
759
  =begin
733
760
  # obtengo cada uno de los spinnings
@@ -735,21 +762,21 @@ module BlackStack
735
762
  a = x.split('|')
736
763
  raise "No variations delimited by '|' inside spinning block." if a.size <= 1
737
764
  }
738
- =end
765
+ =end
739
766
  true
740
767
  end
741
-
768
+
742
769
  # returns true if the text is spinned.
743
770
  # otherwise, returns false.
744
771
  def self.spintax?(s)
745
772
  s.scan(MATCH_CONTENT_SPINNING).size > 0
746
773
  end
747
774
  end # module Spinning
748
-
749
-
750
- # -----------------------------------------------------------------------------------------
775
+
776
+
777
+ # -----------------------------------------------------------------------------------------
751
778
  # Miscelaneus
752
- # -----------------------------------------------------------------------------------------
779
+ # -----------------------------------------------------------------------------------------
753
780
  module Misc
754
781
  # make a Ruby string safe for a filesystem.
755
782
  # References:
@@ -760,7 +787,7 @@ module BlackStack
760
787
  # NOTE: File.basename doesn't work right with Windows paths on Unix
761
788
  # get only the filename, not the whole path
762
789
  name.gsub!(/^.*(\\|\/)/, '')
763
-
790
+
764
791
  # Strip out the non-ascii character
765
792
  name.gsub!(/[^0-9A-Za-z.\-]/, '_')
766
793
  end
@@ -769,9 +796,9 @@ module BlackStack
769
796
  end # module Misc
770
797
 
771
798
 
772
- # -----------------------------------------------------------------------------------------
799
+ # -----------------------------------------------------------------------------------------
773
800
  # Email Appending Functions
774
- # -----------------------------------------------------------------------------------------
801
+ # -----------------------------------------------------------------------------------------
775
802
  module Appending
776
803
  APPEND_PATTERN_FNAME_DOT_LNAME = 0
777
804
  APPEND_PATTERN_FNAME = 1
@@ -779,7 +806,7 @@ module BlackStack
779
806
  APPEND_PATTERN_F_LNAME = 3
780
807
  APPEND_PATTERN_F_DOT_LNAME = 4
781
808
 
782
- #
809
+ #
783
810
  def self.name_pattern(pattern, fname, lname)
784
811
  if (pattern==APPEND_PATTERN_FNAME_DOT_LNAME)
785
812
  return "#{fname}.#{lname}"
@@ -796,13 +823,13 @@ module BlackStack
796
823
  end
797
824
  end
798
825
 
799
- #
826
+ #
800
827
  def self.get_email_variations(first_name, last_name, domain, is_a_big_company)
801
828
  variations = Array.new
802
829
  variations << first_name + "." + last_name + "@" + domain
803
830
  variations << first_name[0] + last_name + "@" + domain
804
831
  variations << first_name + "_" + last_name + "@" + domain
805
- variations << first_name[0] + "." + last_name + "@" + domain
832
+ variations << first_name[0] + "." + last_name + "@" + domain
806
833
  if (is_a_big_company == false)
807
834
  variations << last_name + "@" + domain
808
835
  variations << first_name + "@" + domain
@@ -825,20 +852,20 @@ module BlackStack
825
852
  end
826
853
  end # module Appending
827
854
  end # module String
828
-
829
- # -----------------------------------------------------------------------------------------
855
+
856
+ # -----------------------------------------------------------------------------------------
830
857
  # Network
831
- # -----------------------------------------------------------------------------------------
858
+ # -----------------------------------------------------------------------------------------
832
859
  module Netting
833
860
  CALL_METHOD_GET = 'get'
834
861
  CALL_METHOD_POST = 'post'
835
862
  DEFAULT_SSL_VERIFY_MODE = OpenSSL::SSL::VERIFY_NONE
836
863
  SUCCESS = 'success'
837
-
838
- @@lockfiles = []
864
+
865
+ @@lockfiles = []
839
866
 
840
867
  @@max_api_call_channels = 0 # 0 means infinite
841
-
868
+
842
869
  def self.max_api_call_channels()
843
870
  @@max_api_call_channels
844
871
  end
@@ -850,7 +877,7 @@ module BlackStack
850
877
  def self.set(h)
851
878
  @@max_api_call_channels = h[:max_api_call_channels]
852
879
  @@lockfiles = []
853
-
880
+
854
881
  i = 0
855
882
  while i<@@max_api_call_channels
856
883
  @@lockfiles << File.open("./apicall.channel_#{i.to_s}.lock", "w")
@@ -861,18 +888,18 @@ module BlackStack
861
888
 
862
889
  class ApiCallException < StandardError
863
890
  attr_accessor :description
864
-
891
+
865
892
  def initialize(s)
866
893
  self.description = s
867
894
  end
868
-
895
+
869
896
  def to_s
870
897
  self.description
871
898
  end
872
899
  end
873
-
900
+
874
901
  # New call_get
875
- def self.call_get(url, params = {}, ssl_verify_mode=BlackStack::Netting::DEFAULT_SSL_VERIFY_MODE, support_redirections=true)
902
+ def self.call_get(url, params = {}, ssl_verify_mode=BlackStack::Netting::DEFAULT_SSL_VERIFY_MODE, support_redirections=true)
876
903
  uri = URI(url)
877
904
  uri.query = URI.encode_www_form(params)
878
905
  Net::HTTP.start(uri.host, uri.port, :use_ssl => uri.scheme == 'https', :verify_mode => ssl_verify_mode) do |http|
@@ -887,7 +914,7 @@ module BlackStack
887
914
  end
888
915
  end
889
916
  end
890
-
917
+
891
918
  # Call the API and return th result.
892
919
  #
893
920
  # Unlike `Net::HTTP::Post`, this method support complex json descriptors in order to submit complex data strucutres to access points.
@@ -895,25 +922,25 @@ module BlackStack
895
922
  #
896
923
  # url: valid internet address
897
924
  # body: hash of body to attach in the call
898
- # ssl_verify_mode: you can disabele SSL verification here.
925
+ # ssl_verify_mode: you can disabele SSL verification here.
899
926
  # max_channels: this method use lockfiles to prevent an excesive number of API calls from each datacenter. There is not allowed more simultaneous calls than max_channels.
900
- #
927
+ #
901
928
  # TODO: parameter support_redirections has been deprecated.
902
929
  #
903
930
  def self.call_post(url, body = {}, ssl_verify_mode=BlackStack::Netting::DEFAULT_SSL_VERIFY_MODE, support_redirections=true)
904
- # issue: https://github.com/leandrosardi/mysaas/issues/59
931
+ # issue: https://github.com/leandrosardi/mysaas/issues/59
905
932
  #
906
933
  # when ruby pushes hash of hashes (or hash of arrays), all values are converted into strings.
907
934
  # and arrays are mapped to the last element only.
908
935
  #
909
936
  # the solution is to convert each element of the hash into a string using `.to_json` method.
910
- #
911
- # references:
937
+ #
938
+ # references:
912
939
  # - https://stackoverflow.com/questions/1667630/how-do-i-convert-a-string-object-into-a-hash-object
913
940
  # - https://stackoverflow.com/questions/67572866/how-to-build-complex-json-to-post-to-a-web-service-with-rails-5-2-and-faraday-ge
914
- #
941
+ #
915
942
  # iterate the keys of the hash
916
- #
943
+ #
917
944
  params = {} # not needed for post calls to access points
918
945
  path = URI::parse(url).path
919
946
  domain = url.gsub(/#{Regexp.escape(path)}/, '')
@@ -943,7 +970,7 @@ module BlackStack
943
970
  if (parsed['status']==BlackStack::Netting::SUCCESS)
944
971
  bSuccess = true
945
972
  else
946
- sError = "Status: #{parsed['status'].to_s}. Description: #{parsed['value'].to_s}."
973
+ sError = "Status: #{parsed['status'].to_s}. Description: #{parsed['value'].to_s}."
947
974
  end
948
975
  rescue Errno::ECONNREFUSED => e
949
976
  sError = "Errno::ECONNREFUSED:" + e.to_console
@@ -951,7 +978,7 @@ module BlackStack
951
978
  sError = "Exception:" + e2.to_console
952
979
  end
953
980
  end # while
954
-
981
+
955
982
  if (bSuccess==false)
956
983
  raise "#{sError}"
957
984
  end
@@ -962,7 +989,7 @@ module BlackStack
962
989
  # to: must be a valid path to a folder.
963
990
  def self.download(url, to)
964
991
  uri = URI(url)
965
- domain = uri.host.start_with?('www.') ? uri.host[4..-1] : uri.host
992
+ domain = uri.host.start_with?('www.') ? uri.host[4..-1] : uri.host
966
993
  path = uri.path
967
994
  filename = path.split("/").last
968
995
  Net::HTTP.start(domain) do |http|
@@ -974,7 +1001,7 @@ module BlackStack
974
1001
  end
975
1002
 
976
1003
  # Return the extension of the last path into an URL.
977
- # Example: get_url_extension("http://connect.data.com/sitemap_index.xml?foo_param=foo_value") => ".xml"
1004
+ # Example: get_url_extension("http://connect.data.com/sitemap_index.xml?foo_param=foo_value") => ".xml"
978
1005
  def self.get_url_extension(url)
979
1006
  return File.extname(URI.parse(url).path.to_s)
980
1007
  end
@@ -1015,12 +1042,12 @@ module BlackStack
1015
1042
  httpc = HTTPClient.new
1016
1043
  resp = httpc.get(url)
1017
1044
  res = resp.header['Location']
1018
-
1045
+
1019
1046
  if res.size == 0
1020
1047
  uri = URI.parse(url)
1021
1048
  uri_params = CGI.parse(uri.query)
1022
- redirected_url = uri_params['url'][0]
1023
-
1049
+ redirected_url = uri_params['url'][0]
1050
+
1024
1051
  if ( redirected_url != nil )
1025
1052
  res = redirected_url
1026
1053
  else
@@ -1044,25 +1071,25 @@ module BlackStack
1044
1071
  # => p = CGI::parse(URI.parse(url).query)
1045
1072
  # => La linea de abajo hace un gsbub que hace que esta url siga funcionando como busqueda de google, y ademas se posible parsearla.
1046
1073
  url = url.gsub("webhp#q=", "webhp?q=")
1047
-
1074
+
1048
1075
  return CGI::parse(URI.parse(url).query)
1049
1076
  end
1050
-
1077
+
1051
1078
  # Add a parameter to the url. It doesn't validate if the param already exists.
1052
1079
  def self.add_param(url, param_name, param_value)
1053
1080
  uri = URI(url)
1054
1081
  params = URI.decode_www_form(uri.query || '')
1055
-
1082
+
1056
1083
  if (params.size==0)
1057
1084
  params << [param_name, param_value]
1058
1085
  uri.query = URI.encode_www_form(params)
1059
1086
  return uri.to_s
1060
1087
  else
1061
1088
  uri.query = URI.encode_www_form(params)
1062
- return uri.to_s + "&" + param_name + "=" + param_value
1089
+ return uri.to_s + "&" + param_name + "=" + param_value
1063
1090
  end
1064
1091
  end
1065
-
1092
+
1066
1093
  # Changes the value of a parameter in the url. It doesn't validate if the param already exists.
1067
1094
  def self.change_param(url, param_name, param_value)
1068
1095
  uri = URI(url)
@@ -1072,10 +1099,10 @@ module BlackStack
1072
1099
  uri.query = URI.encode_www_form(params)
1073
1100
  uri.to_s
1074
1101
  end
1075
-
1102
+
1076
1103
  # Change or add the value of a parameter in the url, depending if the parameter already exists or not.
1077
1104
  def self.set_param(url, param_name, param_value)
1078
- params = BlackStack::Netting::params(url)
1105
+ params = BlackStack::Netting::params(url)
1079
1106
  if ( params.has_key?(param_name) == true )
1080
1107
  newurl = BlackStack::Netting::change_param(url, param_name, param_value)
1081
1108
  else
@@ -1083,24 +1110,24 @@ module BlackStack
1083
1110
  end
1084
1111
  return newurl
1085
1112
  end
1086
-
1113
+
1087
1114
  # get the domain from any url
1088
1115
  def self.getDomainFromUrl(url)
1089
- if (url !~ /^http:\/\//i && url !~ /^https:\/\//i)
1116
+ if (url !~ /^http:\/\//i && url !~ /^https:\/\//i)
1090
1117
  url = "http://#{url}"
1091
1118
  end
1092
-
1119
+
1093
1120
  if (URI.parse(url).host == nil)
1094
- raise "Cannot get domain for #{url}"
1121
+ raise "Cannot get domain for #{url}"
1095
1122
  end
1096
-
1123
+
1097
1124
  if (url.to_s.length>0)
1098
1125
  return URI.parse(url).host.sub(/^www\./, '')
1099
1126
  else
1100
1127
  return nil
1101
1128
  end
1102
1129
  end
1103
-
1130
+
1104
1131
  def self.getDomainFromEmail(email)
1105
1132
  if email.email?
1106
1133
  return email.split("@").last
@@ -1108,35 +1135,35 @@ module BlackStack
1108
1135
  raise "getDomainFromEmail: Wrong email format."
1109
1136
  end
1110
1137
  end
1111
-
1138
+
1112
1139
  def self.getWhoisDomains(domain, allow_heuristic_to_avoid_hosting_companies=false)
1113
1140
  a = Array.new
1114
1141
  c = Whois::Client.new
1115
1142
  r = c.lookup(domain)
1116
-
1143
+
1117
1144
  res = r.to_s.scan(/Registrant Email: (#{BlackStack::Strings::MATCH_EMAIL})/).first
1118
1145
  if (res!=nil)
1119
1146
  a << BlackStack::Netting::getDomainFromEmail(res[0].downcase)
1120
1147
  end
1121
-
1148
+
1122
1149
  res = r.to_s.scan(/Admin Email: (#{BlackStack::Strings::MATCH_EMAIL})/).first
1123
1150
  if (res!=nil)
1124
1151
  a << BlackStack::Netting::getDomainFromEmail(res[0].downcase)
1125
1152
  end
1126
-
1153
+
1127
1154
  res = r.to_s.scan(/Tech Email: (#{BlackStack::Strings::MATCH_EMAIL})/).first
1128
1155
  if (res!=nil)
1129
1156
  a << BlackStack::Netting::getDomainFromEmail(res[0].downcase)
1130
1157
  end
1131
-
1158
+
1132
1159
  # remover duplicados
1133
1160
  a = a.uniq
1134
-
1135
- #
1161
+
1162
+ #
1136
1163
  if (allow_heuristic_to_avoid_hosting_companies==true)
1137
1164
  # TODO: develop this feature
1138
1165
  end
1139
-
1166
+
1140
1167
  return a
1141
1168
  end
1142
1169
 
@@ -1164,11 +1191,11 @@ module BlackStack
1164
1191
  raise "Email #{value} is not valid" if !value.email?
1165
1192
  # extract the domain from the email
1166
1193
  domain = value.split('@').last
1167
- #
1194
+ #
1168
1195
  return domain=~/gmail\.com/ || domain=~/hotmail\.com/ || domain=~/outlook\.com/ || domain=~/yahoo\.com/ || domain=~/comcast\.com/ || domain=~/aol\.com/ || domain=~/msn\.com/ || domain=~/sbcglobal\.net/ ? true : false
1169
1196
  end
1170
1197
 
1171
1198
 
1172
1199
  end # module Netting
1173
-
1200
+
1174
1201
  end # module BlackStack
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: blackstack-core
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.2.27
4
+ version: 1.2.29
5
5
  platform: ruby
6
6
  authors:
7
7
  - Leandro Daniel Sardi
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2024-09-05 00:00:00.000000000 Z
11
+ date: 2025-01-13 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: content_spinning