Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

The README.md example doesn't work #63

Open
yart opened this issue Oct 14, 2023 · 15 comments
Open

The README.md example doesn't work #63

yart opened this issue Oct 14, 2023 · 15 comments

Comments

@yart
Copy link

yart commented Oct 14, 2023

My Gemfile:

gem 'dry-configurable', '0.15.0'
gem 'tdlib-ruby'

Trying to run the example from the current README and getting only the following:

/home/yart/work/alcom/coding/tapp/vendor/bundle/ruby/3.2.0/gems/dry-configurable-0.15.0/lib/dry/configurable/dsl.rb:28:in `initialize' [dry-configurable] passing a constructor as a block is deprecated and will be removed in the next major version
Provide a `constructor:` keyword argument instead

/home/yart/work/alcom/coding/tapp/vendor/bundle/ruby/3.2.0/gems/dry-configurable-0.15.0/lib/dry/configurable/dsl.rb:28:in `initialize' [dry-configurable] default value as positional argument to settings is deprecated and will be removed in the nex
t major version
Provide a `default:` keyword argument instead

/home/yart/work/alcom/coding/tapp/vendor/bundle/ruby/3.2.0/gems/dry-configurable-0.15.0/lib/dry/configurable/dsl.rb:28:in `initialize' [dry-configurable] default value as positional argument to settings is deprecated and will be removed in the nex
t major version
Provide a `default:` keyword argument instead

I've been tried ruby 2.7.8 and 3.2.2 — the same result.

The last warning has been repeated several times. And that's all this code does.

I've changed the dry-configurable version according to this issue: #62. I had the same error before.

Who can help me, guys?

@yart
Copy link
Author

yart commented Oct 15, 2023

Changed this part of tdlib-ruby.rb in such a way:

  setting(:client) do
    setting(:api_id) { |val| val.to_i } # before: setting :api_id, &:to_i
    setting :api_hash
    setting :use_test_dc, default: false # before: setting :use_test_dc, false
    setting :database_directory, default: "#{Dir.home}/.tdlib-ruby/db" # before: setting :database_directory, "#{Dir.home}/.tdlib-ruby/db"
    setting :files_directory, default: "#{Dir.home}/.tdlib-ruby/data" # before: setting :files_directory, "#{Dir.home}/.tdlib-ruby/data"
    setting :use_file_database, default: true # before: setting :use_file_database, true
    setting :use_chat_info_database, default: true # before: setting :use_chat_info_database, true
    setting :use_secret_chats, default: true # before: setting :use_secret_chats, true
    setting :use_message_database, default: true # before: setting :use_message_database, true
    setting :system_language_code, default: 'en' # before: setting :system_language_code, 'en'
    setting :device_model, default: 'Ruby TD client' # before: setting :device_model, 'Ruby TD client'
    setting :system_version, default: 'Unknown' # before: setting :system_version, 'Unknown'
    setting :application_version, default: '1.0' # before: setting :application_version, '1.0'
    setting :enable_storage_optimizer, default: true # before: setting :enable_storage_optimizer, true
    setting :ignore_file_names, default: false # before: setting :ignore_file_names, false
  end

Now it's starting without errors and warnings, but the state variable from the example is receiving nothing from this block:

  state = nil

  client.on(TD::Types::Update::AuthorizationState) do |update|
    state =
      case update.authorization_state
      when TD::Types::AuthorizationState::WaitPhoneNumber
        :wait_phone_number
      when TD::Types::AuthorizationState::WaitCode
        :wait_code
      when TD::Types::AuthorizationState::WaitPassword
        :wait_password
      when TD::Types::AuthorizationState::Ready
        :ready
      end
  end

And my code is just busy. But as I got it, it should show me the prompt to put my phone and so on.

From: /home/user/coding/tapp/tel.rb:37 :

    32:   end
    33: 
    34:   client.connect
    35: 
    36:   loop do
 => 37:     binding.pry
    38: 
    39:     case state
    40:     when :wait_phone_number
    41:       puts 'Please, enter your phone number:'
    42:       phone = STDIN.gets.strip

[1] pry(main)> client
=> #<TD::Client:0x00007fe836fdd858
 @alive=true,
 @config=
  {:api_id=>"----------", # my real API ID is shown here
   :api_hash=>"----------------------------", # and the API Hash too
   :use_test_dc=>false,
   :database_directory=>"/home/user/.tdlib-ruby/db",
   :files_directory=>"/home/user/.tdlib-ruby/data",
   :use_file_database=>true,
   :use_chat_info_database=>true,
   :use_secret_chats=>true,
   :use_message_database=>true,
   :system_language_code=>"en",
   :device_model=>"Ruby TD client",
   :system_version=>"Unknown",
   :application_version=>"1.0",
   :enable_storage_optimizer=>true,
   :ignore_file_names=>false},
[2] pry(main)> state
=> nil
[3] pry(main)> !!!

Do you have any idea on how to fix it, guys?

@olegzakharov1416
Copy link

@yart Write if you can solve this problem. I’m also struggling with it now, I have no ideas.

@yart
Copy link
Author

yart commented Oct 17, 2023

@yart Write if you can solve this problem. I’m also struggling with it now, I have no ideas.

Sure. I have an assumption that the problem in one of the following places:

  1. Incorrectly built TDlib — I've been built it using g++ v.13.2.1 installed on Archlinux. I have Clang too, but it produces a strange error when I'm trying to compile the library using this one. So, I'm going to do the following to resolve this possible trouble:
    a. Install TDlib from AUR — it has one
    b. Try to compile it in a Docker container (or find a ready one) with Ubuntu or Alpine and clang
  2. TDlib was changed and needs another set of parameters, so the current one should be changed to the actual state. Will read the TDlib docs to check it.
  3. Some insignificant changes in dry-rb (like it happened with dry-configurable, but not so fatal) or/and in concurrent-ruby. Will read the sources and the change logs to check it.

@KonstantinReido
Copy link

@yart did you find a solution?

@yart
Copy link
Author

yart commented Apr 1, 2024

@yart did you find a solution?

@KonstantinReido I didn't have a time for this yet. But I remember about the problem.

@chhlga
Copy link

chhlga commented Jun 21, 2024

Tdlib changed input params for setTdlibParameters.

tdlib/td#2211 (comment)

@tilvin
Copy link

tilvin commented Jul 5, 2024

Let me share my experience how to work with this lib:

  1. Install TDlib from original resource https://tdlib.github.io/td/build.html?language=Ruby.
    Tick V Install built TDLib to /usr/local instead of placing the files to td/tdlib.

  2. Fork schema
    https://github.com/southbridgeio/tdlib-schema is old and dusty, you will have to fork iе. Add this PR and add some other changes.

The most important one is to change set_tdlib_parameters method to cover this changes in TDlib:

def set_tdlib_parameters(parameters:)
   broadcast(parameters.to_hash.merge('@type' => 'setTdlibParameters'))
end

Also i'm trying to inline schema with Tdlib, maybe i will create a PR soon, but at the moment you can check my fork https://github.com/tilvin/tdlib-schema.

  1. Then authorize:
TD.configure do |config|    
  config.client.api_id = 'api_id'
  config.client.api_hash = 'api_hash'
end
TD::Api.set_log_verbosity_level(1)

client = TD::Client.new

Add debugging puts:

client.on(TD::Types::Update::AuthorizationState) do |update|
   puts "----->  #{update.inspect}"
end
  1. Then connect:

client.connect

  1. Now you suppose to see the auth requirements, something like WaitPhoneNumber.

Pick method from ClientMethods accordingly.

client.set_authentication_phone_number(phone_number: '+7 phone', settings: nil).wait
—> code comes to TG

client.check_authentication_code(code: 'your code’)
  1. Check if it's alive
  client.on('updateNewMessage') do |update|
    puts "========> NEWS updateNewMessage #{update.inspect}"
  end
  1. Tips
    You might see notifications like:
    Uncaught exception in update manager: [TD::Types::ScopeNotificationSettings.new] :sound is missing in Hash input
    Uncaught exception in update manager: Can't find class for updateChatFolders
    Uncaught exception in update manager: Can't find class for updateStoryStealthMode

It comes from rescue, and means that e.g schema's class ScopeNotificationSettings attributes doesn't match with TDlib scopeNotificationSettings anymore. And Tdlib has updateChatFolders class, but your schema don't.

@vladimir-vg
Copy link

vladimir-vg commented Jul 7, 2024

The most important one is to change set_tdlib_parameters method to cover this changes in TDlib:

Hm, on my machine it doesn't see .merge method for TD::Types::TdlibParameters, which is a subclass of Dry::Struct:

-----> #<TD::Types::Update::AuthorizationState authorization_state=#<TD::Types::AuthorizationState::WaitTdlibParameters>>
Uncaught exception in handler TD::UpdateHandler (TD::Types::Update::AuthorizationState): undefined method `merge' for an instance of TD::Types::TdlibParameters

I've used gem 'dry-configurable', '0.15.0', otherwise it just refuses to load tdlib-ruby with no receiver given message.

Tried to replace .merge with .new, with no luck for now.

@tilvin
Copy link

tilvin commented Jul 7, 2024

The most important one is to change set_tdlib_parameters method to cover this changes in TDlib:

Hm, on my machine it doesn't see .merge method for TD::Types::TdlibParameters, which is a subclass of Dry::Struct:

-----> #<TD::Types::Update::AuthorizationState authorization_state=#<TD::Types::AuthorizationState::WaitTdlibParameters>>
Uncaught exception in handler TD::UpdateHandler (TD::Types::Update::AuthorizationState): undefined method `merge' for an instance of TD::Types::TdlibParameters

I've used gem 'dry-configurable', '0.15.0', otherwise it just refuses to load tdlib-ruby with no receiver given message.

Tried to replace .merge with .new, with no luck for now.

Thanks, i forgot this part:
a small update set_tdlib_parameters(parameters: TD::Types::TdlibParameters.new(**@config).to_hash) here

Or

def set_tdlib_parameters(parameters:)
   broadcast(parameters.to_hash.merge('@type' => 'setTdlibParameters'))
end

to change only one gem instead of two.

@vladimir-vg
Copy link

Thanks, i forgot this part:
a small update

Thanks! Indeed, this fix made that error disappear

@tim08
Copy link

tim08 commented Nov 25, 2024

Can anyone tell me what the current set of dependencies is? My current set:

i changed client.rb

  def connect
    on TD::Types::Update::AuthorizationState do |update|
      case update.authorization_state
      when TD::Types::AuthorizationState::WaitTdlibParameters
        # set_tdlib_parameters(parameters: TD::Types::TdlibParameters.new(**@config))
        set_tdlib_parameters(parameters: TD::Types::TdlibParameters.new(**@config).to_hash)
      when TD::Types::AuthorizationState::WaitEncryptionKey
        check_database_encryption_key(encryption_key: TD.config.encryption_key).then do
          @ready_condition_mutex.synchronize do
            @ready = true
            @ready_condition.broadcast
          end
        end
      else
        # do nothing
      end
    end

    @update_manager.run(callback: method(:handle_update))
    ready
  end

I get an error when running the example from the readme (I commented out the logging line to get more information):

C:/Ruby31-x64/lib/ruby/gems/3.1.0/gems/dry-configurable-0.15.0/lib/dry/configurable/dsl.rb:28:in `initialize' [dry-configurable] passing a constructor as a block is deprecated and will be removed in the next major version
Provide a `constructor:` keyword argument instead

[ 3][t 5][1732479222.650855302][Td.cpp:2668][#1][!MultiTd]      Create Td with layer 135, database version 13 and version 35 on 4 threads
[ 3][t 5][1732479222.650944709][Td.cpp:4062][#1][!Td][&td_requests]     Sending update: updateOption {
  name = "version"
  value = optionValueString {
    value = "1.8.0"
  }
}
[ 3][t 5][1732479222.650986671][Td.cpp:4062][#1][!Td][&td_requests]     Sending update: updateAuthorizationState {
  authorization_state = authorizationStateWaitTdlibParameters {
  }
}
[ 3][t 0][1732479222.661797285][Client.cpp:278][&td_requests]   Begin to wait for updates with timeout 30.000000
[ 3][t 0][1732479222.669217824][Client.cpp:291][&td_requests]   End to wait for updates, returning object 0 000001D155E5A5A0
[ 3][t 0][1732479222.689413547][Client.cpp:278][&td_requests]   Begin to wait for updates with timeout 30.000000
[ 3][t 0][1732479222.689558029][Client.cpp:291][&td_requests]   End to wait for updates, returning object 0 000001D1566F67E0
----->  #<TD::Types::Update::AuthorizationState authorization_state=#<TD::Types::AuthorizationState::WaitTdlibParameters>>
[ 3][t 5][1732479222.696928501][Td.cpp:3030][#1][!Td][&td_requests]     Receive request 1: setTdlibParameters {
  parameters = null
}
[ 3][t 5][1732479222.696987390][Td.cpp:4091][#1][!Td][&td_requests]     Sending error for request 1: error { code = 400 message = "Parameters aren't specified" }
[ 3][t 0][1732479222.704432964][Client.cpp:278][&td_requests]   Begin to wait for updates with timeout 30.000000

p.s. I don't know how important it is, but I had to rename tdjson.dll to libtdjson.dll after compilation tdLib, otherwise I'd get an error:

C:/Ruby31-x64/lib/ruby/gems/3.1.0/gems/ffi-1.15.5-x64-mingw-ucrt/lib/ffi/library.rb:145:in `block in ffi_lib': Could not open library 'C:/projects//telegram_c/libtdjson.dll

@tilvin
Copy link

tilvin commented Nov 25, 2024

Can anyone tell me what the current set of dependencies is? My current set:

i changed client.rb

  def connect
    on TD::Types::Update::AuthorizationState do |update|
      case update.authorization_state
      when TD::Types::AuthorizationState::WaitTdlibParameters
        # set_tdlib_parameters(parameters: TD::Types::TdlibParameters.new(**@config))
        set_tdlib_parameters(parameters: TD::Types::TdlibParameters.new(**@config).to_hash)
      when TD::Types::AuthorizationState::WaitEncryptionKey
        check_database_encryption_key(encryption_key: TD.config.encryption_key).then do
          @ready_condition_mutex.synchronize do
            @ready = true
            @ready_condition.broadcast
          end
        end
      else
        # do nothing
      end
    end

    @update_manager.run(callback: method(:handle_update))
    ready
  end

I get an error when running the example from the readme (I commented out the logging line to get more information):

C:/Ruby31-x64/lib/ruby/gems/3.1.0/gems/dry-configurable-0.15.0/lib/dry/configurable/dsl.rb:28:in `initialize' [dry-configurable] passing a constructor as a block is deprecated and will be removed in the next major version
Provide a `constructor:` keyword argument instead

[ 3][t 5][1732479222.650855302][Td.cpp:2668][#1][!MultiTd]      Create Td with layer 135, database version 13 and version 35 on 4 threads
[ 3][t 5][1732479222.650944709][Td.cpp:4062][#1][!Td][&td_requests]     Sending update: updateOption {
  name = "version"
  value = optionValueString {
    value = "1.8.0"
  }
}
[ 3][t 5][1732479222.650986671][Td.cpp:4062][#1][!Td][&td_requests]     Sending update: updateAuthorizationState {
  authorization_state = authorizationStateWaitTdlibParameters {
  }
}
[ 3][t 0][1732479222.661797285][Client.cpp:278][&td_requests]   Begin to wait for updates with timeout 30.000000
[ 3][t 0][1732479222.669217824][Client.cpp:291][&td_requests]   End to wait for updates, returning object 0 000001D155E5A5A0
[ 3][t 0][1732479222.689413547][Client.cpp:278][&td_requests]   Begin to wait for updates with timeout 30.000000
[ 3][t 0][1732479222.689558029][Client.cpp:291][&td_requests]   End to wait for updates, returning object 0 000001D1566F67E0
----->  #<TD::Types::Update::AuthorizationState authorization_state=#<TD::Types::AuthorizationState::WaitTdlibParameters>>
[ 3][t 5][1732479222.696928501][Td.cpp:3030][#1][!Td][&td_requests]     Receive request 1: setTdlibParameters {
  parameters = null
}
[ 3][t 5][1732479222.696987390][Td.cpp:4091][#1][!Td][&td_requests]     Sending error for request 1: error { code = 400 message = "Parameters aren't specified" }
[ 3][t 0][1732479222.704432964][Client.cpp:278][&td_requests]   Begin to wait for updates with timeout 30.000000

p.s. I don't know how important it is, but I had to rename tdjson.dll to libtdjson.dll after compilation tdLib, otherwise I'd get an error:

C:/Ruby31-x64/lib/ruby/gems/3.1.0/gems/ffi-1.15.5-x64-mingw-ucrt/lib/ffi/library.rb:145:in `block in ffi_lib': Could not open library 'C:/projects//telegram_c/libtdjson.dll

Hello, there were major updates introduces in 'tdlib-schema' and 'tdlib-ruby' a few month ago, so i suggest you to use those gems with master branches.
'tdlib-schema' (master branch) is a little bit behind current TDLib version, but at least you should be able to login.

@tim08
Copy link

tim08 commented Nov 25, 2024

@tilvin thanks for the answer, which version should I use TDLib https://github.com/tdlib/td : master or v1.8.0 ?

@tilvin
Copy link

tilvin commented Nov 25, 2024

@tilvin thanks for the answer, which version should I use TDLib https://github.com/tdlib/td : master or v1.8.0
master

@tim08
Copy link

tim08 commented Nov 28, 2024

this might come in handy. I got the authorisation and method of receiving messages from the channel working(text and photo), but when I'm trying to get a video post:

Uncaught exception in update manager: Attribute :video has already been defined

I saw at the very bottom of the documentation information about using ./bin/parse and tried to run:

C:/tg/tdlib-schema/bin/parser:403:in `sort_by': comparison of NilClass with String failed (ArgumentError)
        from C:/tg/tdlib-schema/bin/parser:403:in `<main>'

be sure to take note of: https://github.com/southbridgeio/tdlib-schema/blob/master/bin/parser#L3
After that, everything worked.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

7 participants