SolidusIdentifiers

Welcome to solidus identifiers. This is a simple gem for managing 3rd party identifier for user, products etc. The identifiers are polymorphic so they can be applied to any record.

Installation

Add solidus_identifiers to your Gemfile:

gem 'solidus_identifiers'

Bundle your dependencies and run the installation generator:

bundle
bundle exec rails g solidus_identifiers:install

Usage

Create a Key

Keys are unique by name

Spree::IdentifierKey.create! name: 'facebook-uuid'
Spree::IdentifierKey.create! name: 'google-uuid'
Spree::IdentifierKey.create! name: 'twitter-uuid'
Spree::IdentifierKey.create! name: 'braintree-customer-id'
Spree::IdentifierKey.create! name: 'stripe-customer-id'

Spree::IdentifierKey.create! name: 'stripe-customer-id'
#=> Error! ActiveRecord::RecordNotUnique

Create an Identifier

Identifiers are unique by a composite key of (key, attachable_id, attachable_type). For example, a user can only have one identifier of a specific key.

user = Spree::User.find(10)
key = Spree::IdentifierKey.find_by(name: 'facebook-uuid')

identifier = Spree::Identifier.create!(attachable: user, key: key, value: 'xxxx-xxxx-xxxx')
identifier.attachable == user
#=> true

user.reload
user.identifiers
#=> [<Spree::Identifier xxx>]

Spree::Identifier.create!(attachable: user, key: key, value: 'yyyy-yyyy-yyyy')
#=> Error! ActiveRecord::RecordNotUnique

Note

Identifiers are polymorphic however right now only the Spree::User has an association back to the Spree::Identifier. If you'd like to add an association from another class you can do something like:

module ProductDecorator
  def self.prepended(base)
    base.has_many :identifiers, as: :attachable
  end

  ::Spree.Product.prepend(self)
end

product = Spree::Product.first
product.identifiers

API

Identifier Keys

Get all Keys

Header Parameters

Name Type Required Description
Authorization string required The spree api key
Content-Type string required Must be application/json

Query Parameters

None

Body Parameters

None

Request

GET /api/identifier_keys

{}

Response

{
  "count": 1,
  "total_count": 1,
  "current_page": 1,
  "pages": 1,
  "per_page": 25,
  "identifier_keys": [
    {
      "id": 1,
      "name": "facebook-uuid"
    },
    {
      "id": 2,
      "name": "google-uuid"
    }
  ]
}

Create an Identifier Key

Header Parameters

Name Type Required Description
Authorization string required The spree api key
Content-Type string required Must be application/json

Query Parameters

None

Body Parameters

Name Type Required Description
identifier_key IdentifierKey required The identifier key object

IdentifierKey Parameters

Name Type Required Description
name string required The name for the key

Request

GET /api/identifier_keys

{
 "identifier_key": {
  "name": "google-uuid"
 }
}

Response

{
    "id": 2,
    "name": "google-uuid"
}

Identifiers

Get all identifiers

Header Parameters

Name Type Required Description
Authorization string required The spree api key
Content-Type string required Must be application/json

Query Parameters

None

Body Parameters

None

Request

GET /api/identifiers

{}

Response

{
  "count": 2,
  "total_count": 2,
  "current_page": 1,
  "pages": 1,
  "per_page": 25,
  "identifiers": [
    {
      "id": 1,
      "value": "1111-2222-3333",
      "key": {
        "id": 1,
        "name": "facebook-uuid"
      },
      "attachable": {
        "id": 1,
        "type": "Spree::User"
      }
    },
    {
      "id": 2,
      "value": "1234-1234-1234",
      "key": {
        "id": 2,
        "name": "google-uuid"
      },
      "attachable": {
        "id": 1,
        "type": "Spree::User"
      }
    }
  ]
}

Get single identifier

Header Parameters

Name Type Required Description
Authorization string required The spree api key
Content-Type string required Must be application/json

Query Parameters

Name Type Required Description
id integer required The id of the identifier

Body Parameters

None

Request

GET /api/identifiers/{id}

{}

Response

{
  "id": 1,
  "value": "1111-2222-3333",
  "key": {
    "id": 1,
    "name": "facebook-uuid"
  },
  "attachable": {
    "id": 1,
    "type": "Spree::User"
  }
}

Create an Identifier

Header Parameters

Name Type Required Description
Authorization string required The spree api key
Content-Type string required Must be application/json

Query Parameters

None

Body Parameters

Name Type Required Description
key_id integer required The id of the Identifier Key
attachable_id integer required The id of the attachable record
attachable_type string required The type of the attachable record
value string required The value to assign to the identifier

Identifier Parameters

Name Type Required Description
name string required The name for the key

Request

POST /api/identifiers

{
  "identifier": {
    "key_id": "2",
    "value": "1234-1234-1234",
    "attachable_type": "Spree::User",
    "attachable_id": 1,
 }
}

Response

{
  "id": 2,
  "value": "1234-1234-1234",
  "key": {
    "id": 2,
    "name": "google-uuid"
  },
  "attachable": {
    "id": 1,
    "type": "Spree::User"
  }
}

Testing/Developing

First bundle your dependencies, then run bin/rake. bin/rake will default to building the dummy app if it does not exist, then it will run specs. The dummy app can be regenerated by using bin/rake extension:test_app.

bundle
bin/rake

To run Rubocop static code analysis run

bundle exec rubocop

When testing your application's integration with this extension you may use its factories. Simply add this require statement to your spec_helper:

require 'solidus_identifiers/factories'

Sandbox app

To run this extension in a sandboxed Solidus application you can run bin/sandbox The path for the sandbox app is ./sandbox and bin/rails will forward any Rails command to sandbox/bin/rails.

Example:

$ bin/rails server
=> Booting Puma
=> Rails 6.0.2.1 application starting in development
* Listening on tcp://127.0.0.1:3000
Use Ctrl-C to stop

Releasing

Your new extension version can be released using gem-release like this:

bundle exec gem bump -v VERSION --tag --push --remote upstream && gem release

Copyright (c) 2020 [name of extension creator], released under the New BSD License