Connecting a Bolt Website to Propstack, onOffice and Your CRM Software
PLUS With Bolt, you describe your property website in a chat and Bolt builds the code for it. WP-ImmoMakler supplies the properties from your CRM software, for example from Propstack, onOffice, FlowFact, JustImmo, ImmobilienScout24 (ImmoScout24) or any software with an OpenImmo export, through a REST API. It accepts contact enquiries from your Bolt website and forwards them to your contact persons and, depending on your setup, to your CRM software.
Why this route runs through WordPress and not directly to the API of your CRM software is explained under Connecting an AI website to your CRM software.
Requirements
Section titled “Requirements”- WP-ImmoMakler PLUS or higher, connected to your CRM software
- The headless interface enabled: in the back end of your website (wp-admin) under WP-ImmoMakler → Integrations → Headless, see Setup
- An account with Bolt
Connecting an existing website
Section titled “Connecting an existing website”If you have already created your website with Bolt, usually only the connection to your properties is missing. Your website does not have to be rebuilt for this: the following prompt replaces the sample data with the properties from WP-ImmoMakler, connects the contact form and leaves the design and structure unchanged. Copy it into the chat of your Bolt project and replace https://your-wordpress-address.com with the address of your WordPress website.
My website already shows properties, but still with sample data. Connect it to the WP-ImmoMakler property API, which is described here:https://your-wordpress-address.com/wp-json/immomakler-headless/v1/llms-full.txtRead this description completely first.
The design, layout and components of my website stay unchanged. Replace only the data source. If a property list or detail page is missing, create it in the style of the existing pages.
Property list:- Load the properties via GET /search with fields=summary instead of from the sample data.- Paginate using page and total_pages from the response instead of loading all properties at once.- If my website has filters (property type, marketing type, location, price, rooms, area), build them from GET /site (search.taxonomies, search.ranges, search.orders) and pass them to /search as search parameters. Restore the state of the filters from "applied" in the response and keep it in the URL so that a filtered list stays linkable.- Show a loading state, an error message and a notice when no property matches.
Detail page:- Use the normalised object number (object_number_normalized) in the URL of the detail page and load the property with it via GET /properties/{object_number_normalized}. Never use post_id as an identifier, it changes with every import.- Link from the list to the path from links.frontend_url and align the route of the detail page with it.- If the API responds with 404, show a dedicated "Property not found" page.
Contact form:- If my website has a contact form, connect it to POST /enquiries: with the fields and consents from site.forms.enquiry, a token that the form fetches via GET /spam/token when it is displayed, and the object number (object_number) of the property under "properties".- Show the errors from data.errors of the response on the affected fields.
Displaying data:- Replace every field of the sample data with the matching field of the API. Show numbers, prices and areas with "label" and "value" from the API, do not format "raw" yourself.- Show the data fields in the order in which the API delivers them (fields.property, fields.areas, fields.prices, fields.epass, in the list archive and archive_prices), and leave out fields that a property does not have. Do not invent values and do not keep sample data as a substitute.- Images from media.featured and media.images, each in the matching size from "sizes", with the alternative text from "alt".- Description texts from descriptions as HTML.- Address from address. If geo.exact is false, show an area instead of a point on the map.- Contact person from contact.- Page title and meta description from seo, the structured data from json_ld as <script type="application/ld+json">.
Afterwards, remove the sample data from the project.Creating a new website
Section titled “Creating a new website”Only start with Bolt now, copy the following prompt into it and replace https://your-wordpress-address.com with the address of your WordPress website. Describe the design, page structure and texts in your own words before or after it.
Create a website for my estate agency with a property list, a detail page for each property and a contact form. The properties come from the WP-ImmoMakler property API, which is described here:https://your-wordpress-address.com/wp-json/immomakler-headless/v1/llms-full.txtRead this description completely first.
- Take the name, logo, colours and menus from GET /site.- Load the property list via GET /search with fields=summary, using the filters from site.search, and page through it with page and total_pages. Keep the filters in the URL.- Create the detail page under the normalised object number (object_number_normalized) and load the property via GET /properties/{object_number_normalized}. Link to it from the list using the path from links.frontend_url. Never use post_id as an identifier.- Show the data fields with "label" and "value" in the order in which the API returns them, and omit missing fields. Show images from media in the matching size from "sizes" with the alternative text from "alt", description texts from descriptions as HTML, and the contact person from contact.- If geo.exact is false, show an area on the map instead of a point.- Page title and meta description from seo, structured data from json_ld as <script type="application/ld+json">.- The contact form has the fields from site.forms.enquiry, fetches a token via GET /spam/token when it is displayed and submits to POST /enquiries.Bolt reads the interface description, generates the pages and shows the website with your real properties in the preview.
Allowed origins for the contact form
Section titled “Allowed origins for the contact form”The contact form only submits from addresses that WP-ImmoMakler knows. In the headless settings under “Address of your front end”, enter the published address of your Bolt website. If the form should also work in Bolt’s preview, additionally enter its address under “Allowed origins”. The field does not accept wildcards such as *; each address is entered individually.
Using the API key
Section titled “Using the API key”As long as you do not require the API key for read requests, your Bolt website needs no key: the property data is public, as on your WordPress website.
If you require the key, it must not appear in code that runs in the browser. Add this to the prompt:
The API requires an API key in the header X-ImmoMakler-Key. Read it from the environment variable IMMOMAKLER_API_KEY and call the API only from a server function, never directly from the browser.Create the environment variable in Bolt and, if you publish with a host such as Netlify, there as well; Netlify does not pick up the variables from Bolt by itself, see Deploy your Bolt app to Netlify.
You will find the API key in the back end of your website (wp-admin) under WP-ImmoMakler → Integrations → Headless in the “Access credentials” section. Never write it into the prompt or into the code of the website.
Publishing and search engines
Section titled “Publishing and search engines”Whether search engines see the content of your Bolt website without JavaScript depends on which framework Bolt used to create the project and how you publish it. Ask Bolt to generate the property pages on the server or in advance when publishing, and use your browser’s page source view to check whether the title and description of a property are in the HTML. Background information is available under Your AI website in search engines.
So that links in e-mails and the redirect from WordPress point to your Bolt website, adjust “Path of a property” and “Path of the property list” in the headless settings to its addresses, for example /{archive_slug}/{object_number_normalized}/.