calebhearth / formulaic

Simplify form filling with Capybara

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Rails SimpleForm I18n Formulaic::InputNotFound

LiliyaSabitova opened this issue · comments

Example:

We have simple form for user with email field

f.input :email

and we have simple_form.en.yml

labels:
      user:
        new:
          email: 'Enter your email address'

when we try to fill in form like here

fill_form(
  :user,
  email: email,
  password: password
)

then we get error

Formulaic::InputNotFound:
       Unable to find input "Email".

so we have to do like here

fill_form(
  :user,
  'Enter your email address' => email,
  password: password
)

and we have simple_form.en.yml

labels:
user:
new:
email: 'Enter your email address'

Is that nested under a simple_form key?

https://github.com/plataformatec/simple_form#i18n shows the default lookup format, which should be working if that path is actually simple_form.labels.user.new.email and not just labels.user.new.email, so I'll need to take a look at any configuration you have for simple_form.

Likely places are config/initializers/simple_form.rb and any .rb file that mentions simple_form or SimpleForm.

Specifically I'm looking for the value of SimpleForm.i18n_scope, which if changed will break Formulaic. https://github.com/plataformatec/simple_form/blob/master/lib/simple_form/inputs/base.rb#L191

I'd still like to see the rest of your configuration just in case.

@calebthompson Yep, that nested under simple_form key. Let me show you whole simple_form.en.yml

en:
  simple_form:
    "yes": 'Yes'
    "no": 'No'
    required:
      text: 'required'
      mark: '*'
      # You can uncomment the line below if you need to overwrite the whole required html.
      # When using html, text and mark won't be used.
      # html: '<abbr title="required">*</abbr>'
    error_notification:
      default_message: "Please review the problems below:"
    # Labels and hints examples
    labels:
      user:
        new:
          email: 'Enter your email address'
        edit:
          password: 'Enter new password'
          password_confirmation: 'Confirm your new password'
    hints:
      user:
        password: 'Leave it blank if you dont want to change it'
        current_password: 'We need your current password to confirm your changes'

And also simpleform initializer

# Use this setup block to configure all options available in SimpleForm.
SimpleForm.setup do |config|
  # Wrappers are used by the form builder to generate a
  # complete input. You can remove any component from the
  # wrapper, change the order or even add your own to the
  # stack. The options given below are used to wrap the
  # whole input.
  config.wrappers(
    :default,
    class: :input,
    hint_class: :field_with_hint,
    error_class: :field_with_errors
  ) do |b|
    ## Extensions enabled by default
    # Any of these extensions can be disabled for a
    # given input by passing: `f.input EXTENSION_NAME => false`.
    # You can make any of these extensions optional by
    # renaming `b.use` to `b.optional`.

    # Determines whether to use HTML5 (:email, :url, ...)
    # and required attributes
    b.use :html5

    # Calculates placeholders automatically from I18n
    # You can also pass a string as f.input placeholder: "Placeholder"
    b.use :placeholder

    ## Optional extensions
    # They are disabled unless you pass `f.input EXTENSION_NAME => :lookup`
    # to the input. If so, they will retrieve the values from the model
    # if any exists. If you want to enable the lookup for any of those
    # extensions by default, you can change `b.optional` to `b.use`.

    # Calculates maxlength from length validations for string inputs
    b.optional :maxlength

    # Calculates pattern from format validations for string inputs
    b.optional :pattern

    # Calculates min and max from length validations for numeric inputs
    b.optional :min_max

    # Calculates readonly automatically from readonly attributes
    b.optional :readonly

    ## Inputs
    b.use :label_input
    b.use :hint,  wrap_with: { tag: :span, class: :hint }
    b.use :error, wrap_with: { tag: :span, class: :error }
  end

  config.wrappers :foundation, class: :input, hint_class: :has_hint, error_class: :error do |b|
    b.use :html5
    b.use :placeholder
    b.use :label

    b.optional :maxlength
    b.optional :pattern
    b.optional :min_max
    b.optional :readonly

    b.use :input
    b.use :error, wrap_with: { tag: :small, class: :error }

    # Uncomment the following line to enable hints. The line is commented out by default since Foundation
    # does't provide styles for hints. You will need to provide your own CSS styles for hints.
    b.use :hint,  wrap_with: { tag: :small, class: :hint }
  end

  config.wrappers :with_labels, class: :row, hint_class: :has_hint, error_class: :error do |b|
    b.use :html5
    b.use :placeholder

    b.optional :maxlength
    b.optional :pattern
    b.optional :min_max
    b.optional :readonly

    b.use :label, wrap_with: { class: 'large-4 medium-4 column' }
    b.use :input, wrap_with: { class: 'large-8 medium-8 column' }

    b.wrapper tag: 'div', class: 'large-8 medium-8 column' do |error|
      error.use :error, wrap_with: { tag: :small, class: 'error' }
    end
  end

  # Wrappers for forms and inputs using the Twitter Bootstrap toolkit.
  # Check the Bootstrap docs (http://twitter.github.com/bootstrap)
  # to learn about the different styles for forms and inputs,
  # buttons and other elements.
  config.default_wrapper = :foundation

  # Define the way to render check boxes / radio buttons with labels.
  # Defaults to :nested for bootstrap config.
  #   inline: input + label
  #   nested: label > input
  config.boolean_style = :inline

  # Default class for buttons
  config.button_class = 'button'

  # Method used to tidy up errors. Specify any Rails Array method.
  # :first lists the first message for each field.
  # Use :to_sentence to list all errors for each field.
  # config.error_method = :first

  # Default tag used for error notification helper.
  config.error_notification_tag = :div

  # CSS class to add for error notification helper.
  config.error_notification_class = 'alert-box alert'

  # ID to add for error notification helper.
  # config.error_notification_id = nil

  # Series of attempts to detect a default label method for collection.
  # config.collection_label_methods = [ :to_label, :name, :title, :to_s ]

  # Series of attempts to detect a default value method for collection.
  # config.collection_value_methods = [ :id, :to_s ]

  # You can wrap a collection of radio/check boxes in a pre-defined tag, defaulting to none.
  # config.collection_wrapper_tag = nil

  # You can define the class to use on all collection wrappers. Defaulting to none.
  # config.collection_wrapper_class = nil

  # You can wrap each item in a collection of radio/check boxes with a tag,
  # defaulting to :span. Please note that when using :boolean_style = :nested,
  # SimpleForm will force this option to be a label.
  # config.item_wrapper_tag = :div

  # You can define a class to use in all item wrappers. Defaulting to none.
  # config.item_wrapper_class = 'row'

  # How the label text should be generated altogether with the required text.
  # config.label_text = lambda { |label, required| "#{required} #{label}" }

  # You can define the class to use on all labels. Default is nil.
  # config.label_class = 'column large-4'

  # You can define the class to use on all forms. Default is simple_form.
  config.form_class = 'simple-form'

  # You can define which elements should obtain additional classes
  # config.generate_additional_classes_for = [:wrapper, :label, :input]

  # Whether attributes are required by default (or not). Default is true.
  # config.required_by_default = true

  # Tell browsers whether to use default HTML5 validations (novalidate option).
  # Default is enabled.
  config.browser_validations = false

  # Collection of methods to detect if a file type was given.
  # config.file_methods = [ :mounted_as, :file?, :public_filename ]

  # Custom mappings for input types. This should be a hash containing a regexp
  # to match as key, and the input type that will be used when the field name
  # matches the regexp as value.
  # config.input_mappings = { /count/ => :integer }

  # Default priority for time_zone inputs.
  # config.time_zone_priority = nil

  # Default priority for country inputs.
  # config.country_priority = nil

  # Default size for text inputs.
  # config.default_input_size = 50

  # When false, do not use translations for labels.
  # config.translate_labels = true

  # Automatically discover new inputs in Rails' autoload path.
  # config.inputs_discovery = true

  # Cache SimpleForm inputs discovery
  # config.cache_discovery = !Rails.env.development?
end

Thanks. I'll take a look.

Ah, I found it.

The problem is that while Formulaic::Label is built to support actions other than :create, there's actually no way to specify them in the fill_form interface.

There are a couple of workarounds while I work on a fix. The first is what you've already done, specifying a string as the label.

The second is to try fill_form("user.new", ...), which should override the action here.

This should be fixed, @LiliyaFatykhova @antongudkov