skip to Main Content

I’m using Ruby on Rails, and connecting to the Shopify REST Admin API in my app, to retrieve information for stores. We use the Shopify OAuth2 gem, which handles authentication and access scopes for the API, using the OmniAuth middleware:

Rails.application.config.middleware.use OmniAuth::Builder do
    provider :shopify,
      ENV["SHOPIFY_API_KEY"],
      ENV["SHOPIFY_API_SECRET"],
      scope: 'read_orders,read_products',
      setup: lambda { |env|
        strategy = env['omniauth.strategy']
        shopify_auth_params = Rack::Utils.parse_query(env['QUERY_STRING'])
        shop = if shopify_auth_params.present?
          "https://#{shopify_auth_params['shop']}"
        else
          ''
        end
        strategy.options[:client_options][:site] = shop
      }
end

I want to change which scopes are sent to Shopify during authentication, so some stores get one set of scopes and another store gets a different set. For example, some stores will request the scopes:

read_orders, read_products

While another store requests:

read_orders, read_products, read_inventory

The reason for this is to allow users to choose when they would like to upgrade the app themselves, and not be forced to do so when changing scopes needed by the app.

How I can pass in additional information dynamically?

2

Answers


  1. Chosen as BEST ANSWER

    I solved this by following along on this GitHub issue: https://github.com/Shopify/omniauth-shopify-oauth2/issues/60

    You can pass in the scopes dynamically through the session, and set it in the setup block of OmniAuth:

    Rails.application.config.middleware.use OmniAuth::Builder do
      provider :shopify,
        ShopifyApp.configuration.api_key,
        ShopifyApp.configuration.secret,
        setup: lambda { |env|
          strategy = env['omniauth.strategy']
          session = strategy.session.with_indifferent_access
          env['omniauth.strategy'].options[:scope] = session['shopify.oauth.scope']
          ...
    
    }
    

  2. It might be smarter to think of this in different terms. You probably do not want to use scopes in the world of differentiating your App. Instead, you will focus on actual functionality delivered to the merchant. Pay more, get more. So when you install the App, to make your life easier, you have one set of scope for all installs. You avoid the dreaded modal popup asking for new scopes later, likely resulting in confusion and uninstalls.

    Even if the most restricted App has maximum scope, the merchant cannot do anything with that if you architected your App to limit their functionality. So you might want to build in to your App just that. You decide what the App delivers by inspecting the current subscription plan they are paying for instead of worrying about scope.

    TL:DR; using scope to decide what your App does is a bad idea.

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search