Login
Login with username, email, id, or phone and receive a bearer token or an OTP-required response. OTP is required only when the account has two_auth enabled, or when the organization owner has two_auth_for_team_option enabled (same rules as dashboard Login. On a company subdomain (e.g. user.bull36.com) Host must match account user_domain — mismatch returns success=0 (user does not exist in this company). On a main brand host (bull36.com, www.bull36.com, biz1.co.il, mastrocrm.com, …) domain match is skipped: username/password alone is enough. Custom user_detail.domain hosts are allowed; localhost/IP/unknown brands skip the check. For passwordless OTP login (username = email or user id, no password), use LoginWithOtp instead.
Permissions
- This function can be called without a bearer token.
Action
- Runs the Login function and returns JSON.
Push Service
No push is sent because this function only reads data or returns helper information.
Automation
No automation is run for this function.
Special Instructions
- OTP gate matches dashboard: user.two_auth OR owner.two_auth_for_team_option. Personal Two auth off is not enough if Settings → Two auth for team is on.
- Domain gate (company subdomain only): after password OK, Host must equal {user_domain}.{bull36.com|biz1.co.il|mastrocrm.com}. Wrong subdomain (e.g. eli.bull36.com for user_domain=user) returns success=0, error user_not_in_company — no bearer token.
- Main brand hosts (bull36.com, www.bull36.com, biz1.co.il, mastrocrm.com, …) skip the company domain gate — login with username/password only.
- The same Host ↔ company gate runs on every protected App API when called on a company subdomain. On a main brand host the gate is also skipped.
- When otp_required is true, response may include otp_reason: user_two_auth | two_auth_for_team | force_otp (rate-limit security).
- After success=3, POST the same username/password again with otp from the email.
Required Parameters
| Name | Type | Sample | Explanation |
|---|---|---|---|
passwordpost | string | YOUR PASSWORD | Password for the login identifier. |
Optional Parameters
| Name | Type | Sample | What it gives |
|---|---|---|---|
emailpost | string | [email protected] | Email address for login. You may send username, id, or phone instead. |
usernamepost | string | eli | Username for login. Used when email is not sent. |
idpost | int | 47 | Numeric user id for login. Used when email/username are not sent. |
phonepost | string | 0500000000 | Phone value for login when supported by the account lookup. |
otppost | string | 123456 | One-time code emailed after the first password-only Login when 2FA is required. Send the same username/password again with this otp field. |
Sample Request
{
"url": "\/app\/Login",
"method": "POST",
"body": {
"username": "eli",
"password": "YOUR PASSWORD"
},
"url_user": "https:\/\/{user}.bull36.com\/app\/Login",
"url_domain": "https:\/\/{domain}\/app\/Login"
}Endpoint
POST /app/Login
POST https://{user}.bull36.com/app/Login
POST https://{domain}/app/LoginSample Output
{
"success": "1",
"message": "Login Success",
"token": "YOUR JWT TOKEN",
"token_type": "Bearer",
"expires_in": 43200,
"expires_at": "2026-07-17T13:00:00+00:00",
"redirect_to": "dashboard\/admin"
}OTP Response
{
"success": "3",
"message": "OTP send in your email...!",
"otp_required": true,
"expires_in": 600
}Protection
Login attempts are limited to 8 attempts per 60 seconds. Too many attempts will pause new attempts for 300 seconds.
JavaScript Example
async function getBearerToken({ domain = 'https://{domain}', username, password, otp = '' }) {
const body = new URLSearchParams({ username, password });
if (otp) body.set('otp', otp);
const res = await fetch(`${domain}/app/Login`, {
method: 'POST',
body
});
const data = await res.json();
if (data.otp_required) {
return { otpRequired: true, message: data.message, data };
}
if (!data.token) {
throw new Error(data.message || 'Login failed');
}
return {
token: data.token,
tokenType: data.token_type || 'Bearer',
expiresAt: data.expires_at || null,
raw: data
};
}
// 1) First call returns otp_required and emails a 6-digit code.
const first = await getBearerToken({
domain: 'https://{user}.bull36.com',
username: 'USER EMAIL',
password: 'USER PASSWORD'
});
if (first.otpRequired) {
// 2) Second call completes login with the emailed OTP.
const auth = await getBearerToken({
domain: 'https://{user}.bull36.com',
username: 'USER EMAIL',
password: 'USER PASSWORD',
otp: '123456'
});
console.log(auth.token);
}Error Example
{
"success": "0",
"message": "Login failed"
}