Skip to main content

Workspaces

Base URL: https://app.neuroflash.com/api/workspace-service

Create and manage workspaces.

Create a new workspace with the current customer as the owner

POST/v1/workspaces

creates a new workspace and adds the currently logged in customer as a member with the role owner

Request Body

FieldTypeRequiredDescription
namestringYesName of the workspace

Response

FieldTypeDescription
_embeddedobject
avatarobject
_embeddedobject
signedUrlstring
createdAtstring
createdByUserIdstring
fileNamestring
idstring
signedUrlstring
storageKeystring
updatedAtstring
workspaceIdstring
billingContactobject
activeDiscountstringreadonly synced from stripe: true if a discount is active for this stripe customer
addressLine1stringreadonly synced from stripe: First line of the address of the billing contact
addressLine2stringreadonly synced from stripe: Second line of the address of the billing contact
citystringreadonly synced from stripe: City of the billing contact
countrystringreadonly synced from stripe: Country of the billing contact
createdAtstring
createdByUserIdstring
defaultPaymentCardNumberLastFourDigitsstring
defaultPaymentMethodstring
defaultPaymentMethodCardBrandstring
emailstringEmail address of the billing contact
idstring
importedFromLegacyCustomerIdintegerDeprecated: only needed while import from legacy api is still active ID of the legacy customer this was imported from
namestringName of the billing contact
postalCodestringreadonly synced from stripe: Postal code of the billing contact
statestringreadonly synced from stripe: State of the billing contact
stripeCustomerIdstringStripe customer ID for billing purposes. Could become optional if we add other payment providers
updatedAtstring
currentSubscriptionobject
_embeddedobject
availableWordsintegerdeprecated: remove once the frontend doesn't need it anymore deprecated, moved to rootLevel
newPricingPlanobject
activebooleanset to true when this pricingPlan can be configured on existing and new subscriptions
billingIntervalstring
categoryIdstringID of the category this plan belongs to
displayNamestringname used for internal purposes like the admin-ui or hubspot. Should not be displayed to customers
idstringid of the pricing plan
importedFromLegacyIdinteger
isDefaultbooleanIs this the default plan for new customers?
priceInEuronumberhow much the customer needs to pay for this subscription
pricePerCurrencyobjectA map of string keys to float values
stripeBillingPortalEnabledbooleantrue if subscriptions with this pricingPlan can be self-managed in the stripe billing portal
stripePriceIdstringID of the price in stripe
stripeTrackUsagebooleanwhen true then the usage for subscriptions with this pricingPlan should be tracked in stripe
tierinteger
trialDaysintegerhow many trial days are allowed for this plan
pricingPlanobject
activebooleanset to true when this pricingPlan can be configured on existing and new subscriptions
billingIntervalstring
categoryIdstringID of the category this plan belongs to
displayNamestringname used for internal purposes like the admin-ui or hubspot. Should not be displayed to customers
idstringid of the pricing plan
importedFromLegacyIdinteger
isDefaultbooleanIs this the default plan for new customers?
priceInEuronumberhow much the customer needs to pay for this subscription
pricePerCurrencyobjectA map of string keys to float values
stripeBillingPortalEnabledbooleantrue if subscriptions with this pricingPlan can be self-managed in the stripe billing portal
stripePriceIdstringID of the price in stripe
stripeTrackUsagebooleanwhen true then the usage for subscriptions with this pricingPlan should be tracked in stripe
tierinteger
trialDaysintegerhow many trial days are allowed for this plan
pricingPlanCategoryobject
displayNamestring
idstring
translationKeystring
activebooleanFlag indicating whether the subscription is active. Subscriptions can become inactive if they are paused or have more members than the current plan allows
activeDiscountsarray<string>readonly synced from stripe: true if a discount is active for this stripe subscription
availableWordsintegernumber of words that can still be used in this workspace in the current billing period.
bonusWordsintegerdeprecated: will be moved to a separate limits table/service. Can currently be managed by admins Additional bonus words available for use
createdAtstring
createdByUserIdstring
currencystring
endDatestringreadonly synced from Stripe: date at which this subscription will automatically be cancelled
idstring
importedFromLegacyCustomerIdintegerDeprecated: only needed while import from legacy api is still active ID of the legacy customer this was imported from
isGracePeriodbooleantrue if the subscription will be cancelled at a set date in the future
isTrialbooleantrue if this is currently a trial period
limitRenewalDatestringnext date on which the limits (like words available, images available etc) will be reset. This happens every month, starting with the start of the subscription
nextSubscriptionCycleStartstringreadonly synced from Stripe: Timestamp when the next billing cycle starts. This is NOT necessarily the timestamp when we reset the limits in our system because we reset them monthly even if this is a yearly plan
paymentCardNumberLastFourDigitsstringreadonly synced from Stripe: Last four digits of the payment card number. Uses the default payment on the subscription with a fallback to the payment from the last invoice
paymentMethodCardBrandstring
paymentPausedbooleanreadonly synced from Stripe: true if the payment collection for this subscription is currently paused. Even though stripe intends these subscription to stay active and just be free for a while, we treat subscriptions with payment paused as inactive
paymentTypestring
pricingPlanIdstring
pricingPlanWordsintegerdeprecated: these fields are managed internally but will be moved to the limit structure deprecated: will be moved to a separate limits table/service how many words the pricingPlan from this subscription allows.
sepaPaymentFailedbooleanreadonly synced from Stripe: Flag indicating whether the SEPA payment has failed
spilloverWordsintegerdeprecated: will be moved to a separate limits table/service. Used to calculate the available words next month because you can only keep overspilled words from last month, not accumulate them over multiple months Words carried over from previous month
stripeStatusstring
stripeSubscriptionIdstringStripe subscription ID
stripeSubscriptionItemIdstringID of the subscription item in stripe (subscriptions should only have one item)
trialEndsAtstringreadonly synced from Stripe: Timestamp when the trial period ends
trialStartedAtstringreadonly synced from stripe: if a trial is in progress, date when it started
updatedAtstring
usedWordsintegerdeprecated: will be moved to a separate limits table/service How many words were used in this workspace in the current month
workspaceIdstringID of the workspace this subscription belongs to
billingContactIdstringID of the billing contact for this workspace
createdAtstring
createdByUserIdstring
currentSubscriptionIdstringID of the current subscription for this workspace
firstMemberInvitedAtstringdeprecated Timestamp when the first member was invited to the workspace
firstPaidSubscriptionAtstringIf this workspace ever had a paid subscription, this contains the date at which the first one started
idstring
importedFromLegacyCustomerIdintegerdeprecated Some customers don't have an assigned team in the legacy system as owner but they still need a workspace to which we can import the subscription
importedFromLegacyTeamIdintegerdeprecated: fields that are currently still needed for the legacy system ID of the legacy team this workspace was imported from
keystringHuman readable unique identifier of the workspace
keyIndexintegerUnique auto generated index which is used to generate a unique key
namestringName of the workspace
trialStartedAtstringIf this workspace ever had a subscription with a trial this contains the time when it was started
updatedAtstring

Example

curl -X POST "https://app.neuroflash.com/api/workspace-service/v1/workspaces" \
-H "Authorization: Bearer YOUR_ACCESS_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"name": "string"
}'

Response:

{
"_embedded": {
"avatar": {
"_embedded": {
"signedUrl": "https://storage.googleapis.com/workspaces/550e8400-e29b-41d4-a716-446655440000/avatar/113c0b32-ed6c-4421-b7da-d1faf238eb56.jpg"
},
"createdAt": "2025-01-14T16:20:59Z",
"createdByUserId": "b0920767-2e30-48d3-80ce-268810bc433a",
"fileName": "a2G8Sa7Mn47Je0Lm.png",
"id": "113c0b32-ed6c-4421-b7da-d1faf238eb56",
"signedUrl": "https://storage.googleapis.com/workspaces/550e8400-e29b-41d4-a716-446655440000/avatar/113c0b32-ed6c-4421-b7da-d1faf238eb56.jpg",
"storageKey": "workspaces/550e8400-e29b-41d4-a716-446655440000/avatar",
"updatedAt": "2025-01-14T16:20:59Z",
"workspaceId": "550e8400-e29b-41d4-a716-446655440000"
},
"billingContact": {
"activeDiscount": "string",
"addressLine1": "123 Main St",
"addressLine2": "123 Main St",
"city": "Berlin",
"country": "DE",
"createdAt": "2025-01-14T16:20:59Z",
"createdByUserId": "b0920767-2e30-48d3-80ce-268810bc433a",
"defaultPaymentCardNumberLastFourDigits": "1234",
"defaultPaymentMethod": "acss_debit",
"defaultPaymentMethodCardBrand": "amex",
"email": "max.mustermann@neuroflash.com",
"id": "113c0b32-ed6c-4421-b7da-d1faf238eb56",
"importedFromLegacyCustomerId": 12345,
"name": "Max Mustermann",
"postalCode": "12345",
"state": "Schleswig-Holstein",
"stripeCustomerId": "cus_12345abcdef",
"updatedAt": "2025-01-14T16:20:59Z"
},
"currentSubscription": {
"_embedded": {
"availableWords": 500,
"newPricingPlan": {
"active": "...",
"billingInterval": "...",
"categoryId": "...",
"displayName": "...",
"id": "...",
"importedFromLegacyId": "...",
"isDefault": "...",
"priceInEuro": "...",
"pricePerCurrency": "...",
"stripeBillingPortalEnabled": "...",
"stripePriceId": "...",
"stripeTrackUsage": "...",
"tier": "...",
"trialDays": "..."
},
"pricingPlan": {
"active": "...",
"billingInterval": "...",
"categoryId": "...",
"displayName": "...",
"id": "...",
"importedFromLegacyId": "...",
"isDefault": "...",
"priceInEuro": "...",
"pricePerCurrency": "...",
"stripeBillingPortalEnabled": "...",
"stripePriceId": "...",
"stripeTrackUsage": "...",
"tier": "...",
"trialDays": "..."
},
"pricingPlanCategory": {
"displayName": "...",
"id": "...",
"translationKey": "..."
}
},
"active": true,
"activeDiscounts": [
"string"
],
"availableWords": 500,
"bonusWords": 1000,
"createdAt": "2025-01-14T16:20:59Z",
"createdByUserId": "b0920767-2e30-48d3-80ce-268810bc433a",
"currency": "aed",
"endDate": "string",
"id": "113c0b32-ed6c-4421-b7da-d1faf238eb56",
"importedFromLegacyCustomerId": 12345,
"isGracePeriod": false,
"isTrial": false,
"limitRenewalDate": "string",
"nextSubscriptionCycleStart": "2024-01-01T00:00:00Z",
"paymentCardNumberLastFourDigits": "4242",
"paymentMethodCardBrand": "amex",
"paymentPaused": false,
"paymentType": "acss_debit",
"pricingPlanId": "18d0045a-5850-4bf4-8d5d-3dc8684e2bb2",
"pricingPlanWords": 10000,
"sepaPaymentFailed": false,
"spilloverWords": 500,
"stripeStatus": "active",
"stripeSubscriptionId": "sub_12345abcdef",
"stripeSubscriptionItemId": "sub_item_ad909w0",
"trialEndsAt": "2023-12-31T23:59:59Z",
"trialStartedAt": "string",
"updatedAt": "2025-01-14T16:20:59Z",
"usedWords": 5000,
"workspaceId": "550e8400-e29b-41d4-a716-446655440000"
}
},
"billingContactId": "550e8400-e29b-41d4-a716-446655440000",
"createdAt": "2025-01-14T16:20:59Z",
"createdByUserId": "b0920767-2e30-48d3-80ce-268810bc433a",
"currentSubscriptionId": "550e8400-e29b-41d4-a716-446655440000",
"firstMemberInvitedAt": "2022-01-01T00:00:00Z",
"firstPaidSubscriptionAt": "string",
"id": "113c0b32-ed6c-4421-b7da-d1faf238eb56",
"importedFromLegacyCustomerId": 177,
"importedFromLegacyTeamId": 187,
"key": "NF-GK352",
"keyIndex": 57,
"name": "Online Marketing Team",
"trialStartedAt": "2014-01-02T14:22:00Z",
"updatedAt": "2025-01-14T16:20:59Z"
}

list workspaces visible to the authenticated customer

GET/v1/workspaces

List all workspaces which the authenticated customer is allowed to view

Query Parameters

ParameterTypeDefaultDescription
pageintegerPage number for pagination
sizeintegerNumber of items per page
orderstringOrder direction: asc or desc
sortstringField name to sort by
importedFromLegacyTeamIdsstringFilter by legacyTeamIds from which the workspace was created separated by comma
ownerLegacyCustomerIdsstringFilter by owner legacy customer ids
searchstringsearches in the name, id and key of the workspace

Response

FieldTypeDescription
dataarray<object>
_embeddedobject
avatarobject
_embeddedobject
signedUrlstring
createdAtstring
createdByUserIdstring
fileNamestring
idstring
signedUrlstring
storageKeystring
updatedAtstring
workspaceIdstring
billingContactobject
activeDiscountstringreadonly synced from stripe: true if a discount is active for this stripe customer
addressLine1stringreadonly synced from stripe: First line of the address of the billing contact
addressLine2stringreadonly synced from stripe: Second line of the address of the billing contact
citystringreadonly synced from stripe: City of the billing contact
countrystringreadonly synced from stripe: Country of the billing contact
createdAtstring
createdByUserIdstring
defaultPaymentCardNumberLastFourDigitsstring
defaultPaymentMethodstring
defaultPaymentMethodCardBrandstring
emailstringEmail address of the billing contact
idstring
importedFromLegacyCustomerIdintegerDeprecated: only needed while import from legacy api is still active ID of the legacy customer this was imported from
namestringName of the billing contact
postalCodestringreadonly synced from stripe: Postal code of the billing contact
statestringreadonly synced from stripe: State of the billing contact
stripeCustomerIdstringStripe customer ID for billing purposes. Could become optional if we add other payment providers
updatedAtstring
currentSubscriptionobject
_embeddedobject
availableWordsintegerdeprecated: remove once the frontend doesn't need it anymore deprecated, moved to rootLevel
newPricingPlanobject
activebooleanset to true when this pricingPlan can be configured on existing and new subscriptions
billingIntervalstring
categoryIdstringID of the category this plan belongs to
displayNamestringname used for internal purposes like the admin-ui or hubspot. Should not be displayed to customers
idstringid of the pricing plan
importedFromLegacyIdinteger
isDefaultbooleanIs this the default plan for new customers?
priceInEuronumberhow much the customer needs to pay for this subscription
pricePerCurrencyobjectA map of string keys to float values
stripeBillingPortalEnabledbooleantrue if subscriptions with this pricingPlan can be self-managed in the stripe billing portal
stripePriceIdstringID of the price in stripe
stripeTrackUsagebooleanwhen true then the usage for subscriptions with this pricingPlan should be tracked in stripe
tierinteger
trialDaysintegerhow many trial days are allowed for this plan
pricingPlanobject
activebooleanset to true when this pricingPlan can be configured on existing and new subscriptions
billingIntervalstring
categoryIdstringID of the category this plan belongs to
displayNamestringname used for internal purposes like the admin-ui or hubspot. Should not be displayed to customers
idstringid of the pricing plan
importedFromLegacyIdinteger
isDefaultbooleanIs this the default plan for new customers?
priceInEuronumberhow much the customer needs to pay for this subscription
pricePerCurrencyobjectA map of string keys to float values
stripeBillingPortalEnabledbooleantrue if subscriptions with this pricingPlan can be self-managed in the stripe billing portal
stripePriceIdstringID of the price in stripe
stripeTrackUsagebooleanwhen true then the usage for subscriptions with this pricingPlan should be tracked in stripe
tierinteger
trialDaysintegerhow many trial days are allowed for this plan
pricingPlanCategoryobject
displayNamestring
idstring
translationKeystring
activebooleanFlag indicating whether the subscription is active. Subscriptions can become inactive if they are paused or have more members than the current plan allows
activeDiscountsarray<string>readonly synced from stripe: true if a discount is active for this stripe subscription
availableWordsintegernumber of words that can still be used in this workspace in the current billing period.
bonusWordsintegerdeprecated: will be moved to a separate limits table/service. Can currently be managed by admins Additional bonus words available for use
createdAtstring
createdByUserIdstring
currencystring
endDatestringreadonly synced from Stripe: date at which this subscription will automatically be cancelled
idstring
importedFromLegacyCustomerIdintegerDeprecated: only needed while import from legacy api is still active ID of the legacy customer this was imported from
isGracePeriodbooleantrue if the subscription will be cancelled at a set date in the future
isTrialbooleantrue if this is currently a trial period
limitRenewalDatestringnext date on which the limits (like words available, images available etc) will be reset. This happens every month, starting with the start of the subscription
nextSubscriptionCycleStartstringreadonly synced from Stripe: Timestamp when the next billing cycle starts. This is NOT necessarily the timestamp when we reset the limits in our system because we reset them monthly even if this is a yearly plan
paymentCardNumberLastFourDigitsstringreadonly synced from Stripe: Last four digits of the payment card number. Uses the default payment on the subscription with a fallback to the payment from the last invoice
paymentMethodCardBrandstring
paymentPausedbooleanreadonly synced from Stripe: true if the payment collection for this subscription is currently paused. Even though stripe intends these subscription to stay active and just be free for a while, we treat subscriptions with payment paused as inactive
paymentTypestring
pricingPlanIdstring
pricingPlanWordsintegerdeprecated: these fields are managed internally but will be moved to the limit structure deprecated: will be moved to a separate limits table/service how many words the pricingPlan from this subscription allows.
sepaPaymentFailedbooleanreadonly synced from Stripe: Flag indicating whether the SEPA payment has failed
spilloverWordsintegerdeprecated: will be moved to a separate limits table/service. Used to calculate the available words next month because you can only keep overspilled words from last month, not accumulate them over multiple months Words carried over from previous month
stripeStatusstring
stripeSubscriptionIdstringStripe subscription ID
stripeSubscriptionItemIdstringID of the subscription item in stripe (subscriptions should only have one item)
trialEndsAtstringreadonly synced from Stripe: Timestamp when the trial period ends
trialStartedAtstringreadonly synced from stripe: if a trial is in progress, date when it started
updatedAtstring
usedWordsintegerdeprecated: will be moved to a separate limits table/service How many words were used in this workspace in the current month
workspaceIdstringID of the workspace this subscription belongs to
billingContactIdstringID of the billing contact for this workspace
createdAtstring
createdByUserIdstring
currentSubscriptionIdstringID of the current subscription for this workspace
firstMemberInvitedAtstringdeprecated Timestamp when the first member was invited to the workspace
firstPaidSubscriptionAtstringIf this workspace ever had a paid subscription, this contains the date at which the first one started
idstring
importedFromLegacyCustomerIdintegerdeprecated Some customers don't have an assigned team in the legacy system as owner but they still need a workspace to which we can import the subscription
importedFromLegacyTeamIdintegerdeprecated: fields that are currently still needed for the legacy system ID of the legacy team this workspace was imported from
keystringHuman readable unique identifier of the workspace
keyIndexintegerUnique auto generated index which is used to generate a unique key
namestringName of the workspace
trialStartedAtstringIf this workspace ever had a subscription with a trial this contains the time when it was started
updatedAtstring
pageobject
currentPageinteger
sizeinteger
totalElementsinteger
totalPagesinteger

Example

curl "https://app.neuroflash.com/api/workspace-service/v1/workspaces" \
-H "Authorization: Bearer YOUR_ACCESS_TOKEN"

Response:

{
"data": [
{
"_embedded": {
"avatar": {
"_embedded": "...",
"createdAt": "...",
"createdByUserId": "...",
"fileName": "...",
"id": "...",
"signedUrl": "...",
"storageKey": "...",
"updatedAt": "...",
"workspaceId": "..."
},
"billingContact": {
"activeDiscount": "...",
"addressLine1": "...",
"addressLine2": "...",
"city": "...",
"country": "...",
"createdAt": "...",
"createdByUserId": "...",
"defaultPaymentCardNumberLastFourDigits": "...",
"defaultPaymentMethod": "...",
"defaultPaymentMethodCardBrand": "...",
"email": "...",
"id": "...",
"importedFromLegacyCustomerId": "...",
"name": "...",
"postalCode": "...",
"state": "...",
"stripeCustomerId": "...",
"updatedAt": "..."
},
"currentSubscription": {
"_embedded": "...",
"active": "...",
"activeDiscounts": "...",
"availableWords": "...",
"bonusWords": "...",
"createdAt": "...",
"createdByUserId": "...",
"currency": "...",
"endDate": "...",
"id": "...",
"importedFromLegacyCustomerId": "...",
"isGracePeriod": "...",
"isTrial": "...",
"limitRenewalDate": "...",
"nextSubscriptionCycleStart": "...",
"paymentCardNumberLastFourDigits": "...",
"paymentMethodCardBrand": "...",
"paymentPaused": "...",
"paymentType": "...",
"pricingPlanId": "...",
"pricingPlanWords": "...",
"sepaPaymentFailed": "...",
"spilloverWords": "...",
"stripeStatus": "...",
"stripeSubscriptionId": "...",
"stripeSubscriptionItemId": "...",
"trialEndsAt": "...",
"trialStartedAt": "...",
"updatedAt": "...",
"usedWords": "...",
"workspaceId": "..."
}
},
"billingContactId": "550e8400-e29b-41d4-a716-446655440000",
"createdAt": "2025-01-14T16:20:59Z",
"createdByUserId": "b0920767-2e30-48d3-80ce-268810bc433a",
"currentSubscriptionId": "550e8400-e29b-41d4-a716-446655440000",
"firstMemberInvitedAt": "2022-01-01T00:00:00Z",
"firstPaidSubscriptionAt": "string",
"id": "113c0b32-ed6c-4421-b7da-d1faf238eb56",
"importedFromLegacyCustomerId": 177,
"importedFromLegacyTeamId": 187,
"key": "NF-GK352",
"keyIndex": 57,
"name": "Online Marketing Team",
"trialStartedAt": "2014-01-02T14:22:00Z",
"updatedAt": "2025-01-14T16:20:59Z"
}
],
"page": {
"currentPage": 2,
"size": 10,
"totalElements": 35,
"totalPages": 4
}
}

Get

GET/v1/workspaces/{workspaceId}

Path Parameters

ParameterTypeRequiredDescription
workspaceIdstringYesworkspaceId

Response

FieldTypeDescription
_embeddedobject
avatarobject
_embeddedobject
signedUrlstring
createdAtstring
createdByUserIdstring
fileNamestring
idstring
signedUrlstring
storageKeystring
updatedAtstring
workspaceIdstring
billingContactobject
activeDiscountstringreadonly synced from stripe: true if a discount is active for this stripe customer
addressLine1stringreadonly synced from stripe: First line of the address of the billing contact
addressLine2stringreadonly synced from stripe: Second line of the address of the billing contact
citystringreadonly synced from stripe: City of the billing contact
countrystringreadonly synced from stripe: Country of the billing contact
createdAtstring
createdByUserIdstring
defaultPaymentCardNumberLastFourDigitsstring
defaultPaymentMethodstring
defaultPaymentMethodCardBrandstring
emailstringEmail address of the billing contact
idstring
importedFromLegacyCustomerIdintegerDeprecated: only needed while import from legacy api is still active ID of the legacy customer this was imported from
namestringName of the billing contact
postalCodestringreadonly synced from stripe: Postal code of the billing contact
statestringreadonly synced from stripe: State of the billing contact
stripeCustomerIdstringStripe customer ID for billing purposes. Could become optional if we add other payment providers
updatedAtstring
currentSubscriptionobject
_embeddedobject
availableWordsintegerdeprecated: remove once the frontend doesn't need it anymore deprecated, moved to rootLevel
newPricingPlanobject
activebooleanset to true when this pricingPlan can be configured on existing and new subscriptions
billingIntervalstring
categoryIdstringID of the category this plan belongs to
displayNamestringname used for internal purposes like the admin-ui or hubspot. Should not be displayed to customers
idstringid of the pricing plan
importedFromLegacyIdinteger
isDefaultbooleanIs this the default plan for new customers?
priceInEuronumberhow much the customer needs to pay for this subscription
pricePerCurrencyobjectA map of string keys to float values
stripeBillingPortalEnabledbooleantrue if subscriptions with this pricingPlan can be self-managed in the stripe billing portal
stripePriceIdstringID of the price in stripe
stripeTrackUsagebooleanwhen true then the usage for subscriptions with this pricingPlan should be tracked in stripe
tierinteger
trialDaysintegerhow many trial days are allowed for this plan
pricingPlanobject
activebooleanset to true when this pricingPlan can be configured on existing and new subscriptions
billingIntervalstring
categoryIdstringID of the category this plan belongs to
displayNamestringname used for internal purposes like the admin-ui or hubspot. Should not be displayed to customers
idstringid of the pricing plan
importedFromLegacyIdinteger
isDefaultbooleanIs this the default plan for new customers?
priceInEuronumberhow much the customer needs to pay for this subscription
pricePerCurrencyobjectA map of string keys to float values
stripeBillingPortalEnabledbooleantrue if subscriptions with this pricingPlan can be self-managed in the stripe billing portal
stripePriceIdstringID of the price in stripe
stripeTrackUsagebooleanwhen true then the usage for subscriptions with this pricingPlan should be tracked in stripe
tierinteger
trialDaysintegerhow many trial days are allowed for this plan
pricingPlanCategoryobject
displayNamestring
idstring
translationKeystring
activebooleanFlag indicating whether the subscription is active. Subscriptions can become inactive if they are paused or have more members than the current plan allows
activeDiscountsarray<string>readonly synced from stripe: true if a discount is active for this stripe subscription
availableWordsintegernumber of words that can still be used in this workspace in the current billing period.
bonusWordsintegerdeprecated: will be moved to a separate limits table/service. Can currently be managed by admins Additional bonus words available for use
createdAtstring
createdByUserIdstring
currencystring
endDatestringreadonly synced from Stripe: date at which this subscription will automatically be cancelled
idstring
importedFromLegacyCustomerIdintegerDeprecated: only needed while import from legacy api is still active ID of the legacy customer this was imported from
isGracePeriodbooleantrue if the subscription will be cancelled at a set date in the future
isTrialbooleantrue if this is currently a trial period
limitRenewalDatestringnext date on which the limits (like words available, images available etc) will be reset. This happens every month, starting with the start of the subscription
nextSubscriptionCycleStartstringreadonly synced from Stripe: Timestamp when the next billing cycle starts. This is NOT necessarily the timestamp when we reset the limits in our system because we reset them monthly even if this is a yearly plan
paymentCardNumberLastFourDigitsstringreadonly synced from Stripe: Last four digits of the payment card number. Uses the default payment on the subscription with a fallback to the payment from the last invoice
paymentMethodCardBrandstring
paymentPausedbooleanreadonly synced from Stripe: true if the payment collection for this subscription is currently paused. Even though stripe intends these subscription to stay active and just be free for a while, we treat subscriptions with payment paused as inactive
paymentTypestring
pricingPlanIdstring
pricingPlanWordsintegerdeprecated: these fields are managed internally but will be moved to the limit structure deprecated: will be moved to a separate limits table/service how many words the pricingPlan from this subscription allows.
sepaPaymentFailedbooleanreadonly synced from Stripe: Flag indicating whether the SEPA payment has failed
spilloverWordsintegerdeprecated: will be moved to a separate limits table/service. Used to calculate the available words next month because you can only keep overspilled words from last month, not accumulate them over multiple months Words carried over from previous month
stripeStatusstring
stripeSubscriptionIdstringStripe subscription ID
stripeSubscriptionItemIdstringID of the subscription item in stripe (subscriptions should only have one item)
trialEndsAtstringreadonly synced from Stripe: Timestamp when the trial period ends
trialStartedAtstringreadonly synced from stripe: if a trial is in progress, date when it started
updatedAtstring
usedWordsintegerdeprecated: will be moved to a separate limits table/service How many words were used in this workspace in the current month
workspaceIdstringID of the workspace this subscription belongs to
billingContactIdstringID of the billing contact for this workspace
createdAtstring
createdByUserIdstring
currentSubscriptionIdstringID of the current subscription for this workspace
firstMemberInvitedAtstringdeprecated Timestamp when the first member was invited to the workspace
firstPaidSubscriptionAtstringIf this workspace ever had a paid subscription, this contains the date at which the first one started
idstring
importedFromLegacyCustomerIdintegerdeprecated Some customers don't have an assigned team in the legacy system as owner but they still need a workspace to which we can import the subscription
importedFromLegacyTeamIdintegerdeprecated: fields that are currently still needed for the legacy system ID of the legacy team this workspace was imported from
keystringHuman readable unique identifier of the workspace
keyIndexintegerUnique auto generated index which is used to generate a unique key
namestringName of the workspace
trialStartedAtstringIf this workspace ever had a subscription with a trial this contains the time when it was started
updatedAtstring

Example

curl "https://app.neuroflash.com/api/workspace-service/v1/workspaces/{workspace_id}" \
-H "Authorization: Bearer YOUR_ACCESS_TOKEN"

Response:

{
"_embedded": {
"avatar": {
"_embedded": {
"signedUrl": "https://storage.googleapis.com/workspaces/550e8400-e29b-41d4-a716-446655440000/avatar/113c0b32-ed6c-4421-b7da-d1faf238eb56.jpg"
},
"createdAt": "2025-01-14T16:20:59Z",
"createdByUserId": "b0920767-2e30-48d3-80ce-268810bc433a",
"fileName": "a2G8Sa7Mn47Je0Lm.png",
"id": "113c0b32-ed6c-4421-b7da-d1faf238eb56",
"signedUrl": "https://storage.googleapis.com/workspaces/550e8400-e29b-41d4-a716-446655440000/avatar/113c0b32-ed6c-4421-b7da-d1faf238eb56.jpg",
"storageKey": "workspaces/550e8400-e29b-41d4-a716-446655440000/avatar",
"updatedAt": "2025-01-14T16:20:59Z",
"workspaceId": "550e8400-e29b-41d4-a716-446655440000"
},
"billingContact": {
"activeDiscount": "string",
"addressLine1": "123 Main St",
"addressLine2": "123 Main St",
"city": "Berlin",
"country": "DE",
"createdAt": "2025-01-14T16:20:59Z",
"createdByUserId": "b0920767-2e30-48d3-80ce-268810bc433a",
"defaultPaymentCardNumberLastFourDigits": "1234",
"defaultPaymentMethod": "acss_debit",
"defaultPaymentMethodCardBrand": "amex",
"email": "max.mustermann@neuroflash.com",
"id": "113c0b32-ed6c-4421-b7da-d1faf238eb56",
"importedFromLegacyCustomerId": 12345,
"name": "Max Mustermann",
"postalCode": "12345",
"state": "Schleswig-Holstein",
"stripeCustomerId": "cus_12345abcdef",
"updatedAt": "2025-01-14T16:20:59Z"
},
"currentSubscription": {
"_embedded": {
"availableWords": 500,
"newPricingPlan": {
"active": "...",
"billingInterval": "...",
"categoryId": "...",
"displayName": "...",
"id": "...",
"importedFromLegacyId": "...",
"isDefault": "...",
"priceInEuro": "...",
"pricePerCurrency": "...",
"stripeBillingPortalEnabled": "...",
"stripePriceId": "...",
"stripeTrackUsage": "...",
"tier": "...",
"trialDays": "..."
},
"pricingPlan": {
"active": "...",
"billingInterval": "...",
"categoryId": "...",
"displayName": "...",
"id": "...",
"importedFromLegacyId": "...",
"isDefault": "...",
"priceInEuro": "...",
"pricePerCurrency": "...",
"stripeBillingPortalEnabled": "...",
"stripePriceId": "...",
"stripeTrackUsage": "...",
"tier": "...",
"trialDays": "..."
},
"pricingPlanCategory": {
"displayName": "...",
"id": "...",
"translationKey": "..."
}
},
"active": true,
"activeDiscounts": [
"string"
],
"availableWords": 500,
"bonusWords": 1000,
"createdAt": "2025-01-14T16:20:59Z",
"createdByUserId": "b0920767-2e30-48d3-80ce-268810bc433a",
"currency": "aed",
"endDate": "string",
"id": "113c0b32-ed6c-4421-b7da-d1faf238eb56",
"importedFromLegacyCustomerId": 12345,
"isGracePeriod": false,
"isTrial": false,
"limitRenewalDate": "string",
"nextSubscriptionCycleStart": "2024-01-01T00:00:00Z",
"paymentCardNumberLastFourDigits": "4242",
"paymentMethodCardBrand": "amex",
"paymentPaused": false,
"paymentType": "acss_debit",
"pricingPlanId": "18d0045a-5850-4bf4-8d5d-3dc8684e2bb2",
"pricingPlanWords": 10000,
"sepaPaymentFailed": false,
"spilloverWords": 500,
"stripeStatus": "active",
"stripeSubscriptionId": "sub_12345abcdef",
"stripeSubscriptionItemId": "sub_item_ad909w0",
"trialEndsAt": "2023-12-31T23:59:59Z",
"trialStartedAt": "string",
"updatedAt": "2025-01-14T16:20:59Z",
"usedWords": 5000,
"workspaceId": "550e8400-e29b-41d4-a716-446655440000"
}
},
"billingContactId": "550e8400-e29b-41d4-a716-446655440000",
"createdAt": "2025-01-14T16:20:59Z",
"createdByUserId": "b0920767-2e30-48d3-80ce-268810bc433a",
"currentSubscriptionId": "550e8400-e29b-41d4-a716-446655440000",
"firstMemberInvitedAt": "2022-01-01T00:00:00Z",
"firstPaidSubscriptionAt": "string",
"id": "113c0b32-ed6c-4421-b7da-d1faf238eb56",
"importedFromLegacyCustomerId": 177,
"importedFromLegacyTeamId": 187,
"key": "NF-GK352",
"keyIndex": 57,
"name": "Online Marketing Team",
"trialStartedAt": "2014-01-02T14:22:00Z",
"updatedAt": "2025-01-14T16:20:59Z"
}

Update

PUT/v1/workspaces/{workspaceId}

Path Parameters

ParameterTypeRequiredDescription
workspaceIdstringYesworkspaceId

Request Body

FieldTypeRequiredDescription
namestringYesName of the workspace

Response

FieldTypeDescription
_embeddedobject
avatarobject
_embeddedobject
signedUrlstring
createdAtstring
createdByUserIdstring
fileNamestring
idstring
signedUrlstring
storageKeystring
updatedAtstring
workspaceIdstring
billingContactobject
activeDiscountstringreadonly synced from stripe: true if a discount is active for this stripe customer
addressLine1stringreadonly synced from stripe: First line of the address of the billing contact
addressLine2stringreadonly synced from stripe: Second line of the address of the billing contact
citystringreadonly synced from stripe: City of the billing contact
countrystringreadonly synced from stripe: Country of the billing contact
createdAtstring
createdByUserIdstring
defaultPaymentCardNumberLastFourDigitsstring
defaultPaymentMethodstring
defaultPaymentMethodCardBrandstring
emailstringEmail address of the billing contact
idstring
importedFromLegacyCustomerIdintegerDeprecated: only needed while import from legacy api is still active ID of the legacy customer this was imported from
namestringName of the billing contact
postalCodestringreadonly synced from stripe: Postal code of the billing contact
statestringreadonly synced from stripe: State of the billing contact
stripeCustomerIdstringStripe customer ID for billing purposes. Could become optional if we add other payment providers
updatedAtstring
currentSubscriptionobject
_embeddedobject
availableWordsintegerdeprecated: remove once the frontend doesn't need it anymore deprecated, moved to rootLevel
newPricingPlanobject
activebooleanset to true when this pricingPlan can be configured on existing and new subscriptions
billingIntervalstring
categoryIdstringID of the category this plan belongs to
displayNamestringname used for internal purposes like the admin-ui or hubspot. Should not be displayed to customers
idstringid of the pricing plan
importedFromLegacyIdinteger
isDefaultbooleanIs this the default plan for new customers?
priceInEuronumberhow much the customer needs to pay for this subscription
pricePerCurrencyobjectA map of string keys to float values
stripeBillingPortalEnabledbooleantrue if subscriptions with this pricingPlan can be self-managed in the stripe billing portal
stripePriceIdstringID of the price in stripe
stripeTrackUsagebooleanwhen true then the usage for subscriptions with this pricingPlan should be tracked in stripe
tierinteger
trialDaysintegerhow many trial days are allowed for this plan
pricingPlanobject
activebooleanset to true when this pricingPlan can be configured on existing and new subscriptions
billingIntervalstring
categoryIdstringID of the category this plan belongs to
displayNamestringname used for internal purposes like the admin-ui or hubspot. Should not be displayed to customers
idstringid of the pricing plan
importedFromLegacyIdinteger
isDefaultbooleanIs this the default plan for new customers?
priceInEuronumberhow much the customer needs to pay for this subscription
pricePerCurrencyobjectA map of string keys to float values
stripeBillingPortalEnabledbooleantrue if subscriptions with this pricingPlan can be self-managed in the stripe billing portal
stripePriceIdstringID of the price in stripe
stripeTrackUsagebooleanwhen true then the usage for subscriptions with this pricingPlan should be tracked in stripe
tierinteger
trialDaysintegerhow many trial days are allowed for this plan
pricingPlanCategoryobject
displayNamestring
idstring
translationKeystring
activebooleanFlag indicating whether the subscription is active. Subscriptions can become inactive if they are paused or have more members than the current plan allows
activeDiscountsarray<string>readonly synced from stripe: true if a discount is active for this stripe subscription
availableWordsintegernumber of words that can still be used in this workspace in the current billing period.
bonusWordsintegerdeprecated: will be moved to a separate limits table/service. Can currently be managed by admins Additional bonus words available for use
createdAtstring
createdByUserIdstring
currencystring
endDatestringreadonly synced from Stripe: date at which this subscription will automatically be cancelled
idstring
importedFromLegacyCustomerIdintegerDeprecated: only needed while import from legacy api is still active ID of the legacy customer this was imported from
isGracePeriodbooleantrue if the subscription will be cancelled at a set date in the future
isTrialbooleantrue if this is currently a trial period
limitRenewalDatestringnext date on which the limits (like words available, images available etc) will be reset. This happens every month, starting with the start of the subscription
nextSubscriptionCycleStartstringreadonly synced from Stripe: Timestamp when the next billing cycle starts. This is NOT necessarily the timestamp when we reset the limits in our system because we reset them monthly even if this is a yearly plan
paymentCardNumberLastFourDigitsstringreadonly synced from Stripe: Last four digits of the payment card number. Uses the default payment on the subscription with a fallback to the payment from the last invoice
paymentMethodCardBrandstring
paymentPausedbooleanreadonly synced from Stripe: true if the payment collection for this subscription is currently paused. Even though stripe intends these subscription to stay active and just be free for a while, we treat subscriptions with payment paused as inactive
paymentTypestring
pricingPlanIdstring
pricingPlanWordsintegerdeprecated: these fields are managed internally but will be moved to the limit structure deprecated: will be moved to a separate limits table/service how many words the pricingPlan from this subscription allows.
sepaPaymentFailedbooleanreadonly synced from Stripe: Flag indicating whether the SEPA payment has failed
spilloverWordsintegerdeprecated: will be moved to a separate limits table/service. Used to calculate the available words next month because you can only keep overspilled words from last month, not accumulate them over multiple months Words carried over from previous month
stripeStatusstring
stripeSubscriptionIdstringStripe subscription ID
stripeSubscriptionItemIdstringID of the subscription item in stripe (subscriptions should only have one item)
trialEndsAtstringreadonly synced from Stripe: Timestamp when the trial period ends
trialStartedAtstringreadonly synced from stripe: if a trial is in progress, date when it started
updatedAtstring
usedWordsintegerdeprecated: will be moved to a separate limits table/service How many words were used in this workspace in the current month
workspaceIdstringID of the workspace this subscription belongs to
billingContactIdstringID of the billing contact for this workspace
createdAtstring
createdByUserIdstring
currentSubscriptionIdstringID of the current subscription for this workspace
firstMemberInvitedAtstringdeprecated Timestamp when the first member was invited to the workspace
firstPaidSubscriptionAtstringIf this workspace ever had a paid subscription, this contains the date at which the first one started
idstring
importedFromLegacyCustomerIdintegerdeprecated Some customers don't have an assigned team in the legacy system as owner but they still need a workspace to which we can import the subscription
importedFromLegacyTeamIdintegerdeprecated: fields that are currently still needed for the legacy system ID of the legacy team this workspace was imported from
keystringHuman readable unique identifier of the workspace
keyIndexintegerUnique auto generated index which is used to generate a unique key
namestringName of the workspace
trialStartedAtstringIf this workspace ever had a subscription with a trial this contains the time when it was started
updatedAtstring

Example

curl -X PUT "https://app.neuroflash.com/api/workspace-service/v1/workspaces/{workspace_id}" \
-H "Authorization: Bearer YOUR_ACCESS_TOKEN" \
-H "Content-Type: application/json" \
-d '{
"name": "string"
}'

Response:

{
"_embedded": {
"avatar": {
"_embedded": {
"signedUrl": "https://storage.googleapis.com/workspaces/550e8400-e29b-41d4-a716-446655440000/avatar/113c0b32-ed6c-4421-b7da-d1faf238eb56.jpg"
},
"createdAt": "2025-01-14T16:20:59Z",
"createdByUserId": "b0920767-2e30-48d3-80ce-268810bc433a",
"fileName": "a2G8Sa7Mn47Je0Lm.png",
"id": "113c0b32-ed6c-4421-b7da-d1faf238eb56",
"signedUrl": "https://storage.googleapis.com/workspaces/550e8400-e29b-41d4-a716-446655440000/avatar/113c0b32-ed6c-4421-b7da-d1faf238eb56.jpg",
"storageKey": "workspaces/550e8400-e29b-41d4-a716-446655440000/avatar",
"updatedAt": "2025-01-14T16:20:59Z",
"workspaceId": "550e8400-e29b-41d4-a716-446655440000"
},
"billingContact": {
"activeDiscount": "string",
"addressLine1": "123 Main St",
"addressLine2": "123 Main St",
"city": "Berlin",
"country": "DE",
"createdAt": "2025-01-14T16:20:59Z",
"createdByUserId": "b0920767-2e30-48d3-80ce-268810bc433a",
"defaultPaymentCardNumberLastFourDigits": "1234",
"defaultPaymentMethod": "acss_debit",
"defaultPaymentMethodCardBrand": "amex",
"email": "max.mustermann@neuroflash.com",
"id": "113c0b32-ed6c-4421-b7da-d1faf238eb56",
"importedFromLegacyCustomerId": 12345,
"name": "Max Mustermann",
"postalCode": "12345",
"state": "Schleswig-Holstein",
"stripeCustomerId": "cus_12345abcdef",
"updatedAt": "2025-01-14T16:20:59Z"
},
"currentSubscription": {
"_embedded": {
"availableWords": 500,
"newPricingPlan": {
"active": "...",
"billingInterval": "...",
"categoryId": "...",
"displayName": "...",
"id": "...",
"importedFromLegacyId": "...",
"isDefault": "...",
"priceInEuro": "...",
"pricePerCurrency": "...",
"stripeBillingPortalEnabled": "...",
"stripePriceId": "...",
"stripeTrackUsage": "...",
"tier": "...",
"trialDays": "..."
},
"pricingPlan": {
"active": "...",
"billingInterval": "...",
"categoryId": "...",
"displayName": "...",
"id": "...",
"importedFromLegacyId": "...",
"isDefault": "...",
"priceInEuro": "...",
"pricePerCurrency": "...",
"stripeBillingPortalEnabled": "...",
"stripePriceId": "...",
"stripeTrackUsage": "...",
"tier": "...",
"trialDays": "..."
},
"pricingPlanCategory": {
"displayName": "...",
"id": "...",
"translationKey": "..."
}
},
"active": true,
"activeDiscounts": [
"string"
],
"availableWords": 500,
"bonusWords": 1000,
"createdAt": "2025-01-14T16:20:59Z",
"createdByUserId": "b0920767-2e30-48d3-80ce-268810bc433a",
"currency": "aed",
"endDate": "string",
"id": "113c0b32-ed6c-4421-b7da-d1faf238eb56",
"importedFromLegacyCustomerId": 12345,
"isGracePeriod": false,
"isTrial": false,
"limitRenewalDate": "string",
"nextSubscriptionCycleStart": "2024-01-01T00:00:00Z",
"paymentCardNumberLastFourDigits": "4242",
"paymentMethodCardBrand": "amex",
"paymentPaused": false,
"paymentType": "acss_debit",
"pricingPlanId": "18d0045a-5850-4bf4-8d5d-3dc8684e2bb2",
"pricingPlanWords": 10000,
"sepaPaymentFailed": false,
"spilloverWords": 500,
"stripeStatus": "active",
"stripeSubscriptionId": "sub_12345abcdef",
"stripeSubscriptionItemId": "sub_item_ad909w0",
"trialEndsAt": "2023-12-31T23:59:59Z",
"trialStartedAt": "string",
"updatedAt": "2025-01-14T16:20:59Z",
"usedWords": 5000,
"workspaceId": "550e8400-e29b-41d4-a716-446655440000"
}
},
"billingContactId": "550e8400-e29b-41d4-a716-446655440000",
"createdAt": "2025-01-14T16:20:59Z",
"createdByUserId": "b0920767-2e30-48d3-80ce-268810bc433a",
"currentSubscriptionId": "550e8400-e29b-41d4-a716-446655440000",
"firstMemberInvitedAt": "2022-01-01T00:00:00Z",
"firstPaidSubscriptionAt": "string",
"id": "113c0b32-ed6c-4421-b7da-d1faf238eb56",
"importedFromLegacyCustomerId": 177,
"importedFromLegacyTeamId": 187,
"key": "NF-GK352",
"keyIndex": 57,
"name": "Online Marketing Team",
"trialStartedAt": "2014-01-02T14:22:00Z",
"updatedAt": "2025-01-14T16:20:59Z"
}

Delete

DELETE/v1/workspaces/{workspaceId}

Path Parameters

ParameterTypeRequiredDescription
workspaceIdstringYesworkspaceId

Example

curl -X DELETE "https://app.neuroflash.com/api/workspace-service/v1/workspaces/{workspace_id}" \
-H "Authorization: Bearer YOUR_ACCESS_TOKEN"