Skip to main content

Frontend CORS Solutions

During frontend development, Cross-Origin Resource Sharing (CORS) is a common issue. This document introduces various solutions for solving CORS problems in projects created with Lovrabet CLI.

What is the CORS Problem?

CORS refers to browsers restricting web pages from requesting resources from another domain for security reasons. When the protocol, domain, or port is different, CORS issues arise.

Important Note: Even if they are both subdomains of *.lovrabet.com, dev.lovrabet.com and api.lovrabet.com are still different domains and constitute cross-origin requests. It's just that through configuring CORS whitelist, such cross-origin access is allowed.

CORS Determination Criteria

Browsers determine whether a request is cross-origin by checking if the following three elements are exactly the same:

  • Protocol: http vs https
  • Domain: dev.lovrabet.com vs api.lovrabet.com
  • Port: 80 vs 443 vs 3000

CORS Examples

Frontend URLAPI URLCross-Origin?Explanation
http://localhost:3000https://api.lovrabet.comYesProtocol, domain, and port are all different
https://dev.lovrabet.comhttps://api.lovrabet.comYesDifferent domain (although both are lovrabet.com subdomains)
https://dev.lovrabet.comhttps://dev.lovrabet.comSame OriginExactly the same domain
http://example.com:80http://example.com:443YesDifferent ports
https://example.comhttp://example.comYesDifferent protocols

Note: dev.lovrabet.comapi.lovrabet.com are both subdomains of lovrabet.com, but this is still cross-origin. It's just that through server-side CORS whitelist configuration, such cross-origin access is allowed, so no CORS error occurs.

Solutions Overview

Lovrabet CLI provides multiple solutions for CORS issues, you can choose based on your scenario:

SolutionApplicable ScenarioProsCons
Solution 1: Use dev.lovrabet.comDevelopment phaseAuto-configured, no extra setupDevelopment only
Solution 2: Server CORS ConfigNeed to access own APISimple and directRequires server access
Solution 3: Server ProxyComplex business scenariosFlexible, can add business logicRequires extra development
Solution 4: Independent DeploymentProduction environmentFully autonomous, no CORS issuesRequires deployment resources

How It Works

When starting the project with lovrabet start, CLI automatically maps your local project to the dev.lovrabet.com development domain.

Important: Although dev.lovrabet.com and api.lovrabet.com are both subdomains of lovrabet.com, they are still different domains and constitute cross-origin requests. However, dev.lovrabet.com has been added to the Lovrabet platform's CORS whitelist, and the server allows cross-origin requests from dev.lovrabet.com, so no CORS error occurs.

Usage

# Start development server
lovrabet start

# Access URL will be automatically mapped to
# https://dev.lovrabet.com/your-app-path

Advantages

  • Zero Configuration: No extra setup needed, works out of the box
  • Auto Mapping: CLI automatically handles domain mapping and HTTPS
  • Whitelist Configured: dev.lovrabet.com is already in CORS whitelist
  • Developer Friendly: Supports hot reload, smooth development experience

Notes

  • This solution is only for development environment
  • Need to log in to Lovrabet platform to use dev.lovrabet.com domain
  • If accessing non-*.lovrabet.com APIs, CORS issues may still occur

Solution 2: Server CORS Configuration

Applicable Scenario

When your frontend application runs on dev.lovrabet.com but needs to access your own server's API, you may encounter CORS issues. You can configure CORS on your server to allow dev.lovrabet.com access.

Configuration Examples

Node.js (Express)

const express = require('express');
const app = express();

// Allow dev.lovrabet.com cross-origin access
app.use((req, res, next) => {
res.header('Access-Control-Allow-Origin', 'https://dev.lovrabet.com');
res.header('Access-Control-Allow-Methods', 'GET, POST, PUT, DELETE, OPTIONS');
res.header('Access-Control-Allow-Headers', 'Content-Type, Authorization');
res.header('Access-Control-Allow-Credentials', 'true');

if (req.method === 'OPTIONS') {
return res.sendStatus(200);
}
next();
});

Nginx

server {
listen 80;
server_name your-api-domain.com;

location / {
# Allow dev.lovrabet.com cross-origin access
add_header 'Access-Control-Allow-Origin' 'https://dev.lovrabet.com';
add_header 'Access-Control-Allow-Methods' 'GET, POST, PUT, DELETE, OPTIONS';
add_header 'Access-Control-Allow-Headers' 'Content-Type, Authorization';
add_header 'Access-Control-Allow-Credentials' 'true';

if ($request_method = 'OPTIONS') {
return 204;
}

# Your API handling logic
proxy_pass http://backend;
}
}

Spring Boot (Java)

@Configuration
public class CorsConfig {
@Bean
public WebMvcConfigurer corsConfigurer() {
return new WebMvcConfigurer() {
@Override
public void addCorsMappings(CorsRegistry registry) {
registry.addMapping("/**")
.allowedOrigins("https://dev.lovrabet.com")
.allowedMethods("GET", "POST", "PUT", "DELETE", "OPTIONS")
.allowedHeaders("*")
.allowCredentials(true);
}
};
}
}

Advantages

  • Simple and Direct: Only need to configure once on server side
  • Good Performance: Browser directly accesses API, no middleware
  • Flexible: Can precisely control allowed domains and methods

Notes

  • Requires server administrator access
  • For production, recommend using environment variables to configure allowed domains
  • For security, don't use wildcard * to allow all domains

Solution 3: Server Proxy (API Relay)

Applicable Scenario

When you cannot modify server CORS configuration, or need to add business logic, authentication, or data transformation in requests, use the server proxy solution.

How It Works

Frontend doesn't call target API directly, but calls its own server endpoint, which forwards requests to the target API. This allows:

  • Bypassing browser CORS restrictions
  • Adding business logic on server side
  • Hiding API implementation details
  • Unified error handling and logging

Implementation Examples

Refer to Scenario 3: API Proxy in the Next.js Demo Project.

Next.js API Route Example

// app/api/proxy/data/route.ts
import { NextRequest, NextResponse } from "next/server";
import { createServerClient } from "@/lib/sdk-client";

export async function GET(request: NextRequest) {
try {
const searchParams = request.nextUrl.searchParams;
const page = searchParams.get("page") || "1";
const size = searchParams.get("size") || "10";

// Create client on server side (no CORS issues)
const client = createServerClient();
const model = client.getModel(0);

// Call SDK to get data
const response = await model.filter({
page: parseInt(page),
pageSize: parseInt(size),
});

// Return data to frontend
return NextResponse.json({
success: true,
data: response,
});
} catch (error) {
return NextResponse.json(
{
success: false,
error: error instanceof Error ? error.message : "Unknown error",
},
{ status: 500 }
);
}
}

Frontend Call

// Frontend gets data through its own API route
const fetchData = async () => {
const response = await fetch('/api/proxy/data?page=1&size=10');
const result = await response.json();

if (result.success) {
// Use data
console.log(result.data);
}
};

Express.js Example

const express = require('express');
const axios = require('axios');
const app = express();

app.use(express.json());

// Proxy API requests
app.get('/api/proxy/data', async (req, res) => {
try {
const { page, size } = req.query;

// Call target API on server side (no CORS restrictions)
const response = await axios.get('https://api.target.com/data', {
params: { page, size },
headers: {
'Authorization': `Bearer ${process.env.API_TOKEN}`,
},
});

// Can add business logic, data transformation here
const transformedData = transformData(response.data);

res.json({
success: true,
data: transformedData,
});
} catch (error) {
res.status(500).json({
success: false,
error: error.message,
});
}
});

function transformData(data) {
// Data transformation logic
return data;
}

Advantages

  • Completely Bypasses CORS: No CORS restrictions on server side
  • Flexible and Controllable: Can add business logic, authentication
  • Hides Implementation: Frontend doesn't need to know target API details
  • Unified Handling: Can unify error handling, logging, caching, etc.

Notes

  • Requires additional server resources
  • Adds to request chain, may have slight latency
  • Need to handle server-side errors and timeouts

Complete Example

See the complete implementation: openapi-nextjs-demo project's scenario3-proxy scenario.


Solution 4: Independent Deployment to Your Own Server

Applicable Scenario

After development is complete, deploy the project independently to your own server using your own domain. This eliminates CORS issues because both frontend and API are under your control.

Deployment Steps

1. Build Production Version

# Build project
lovrabet build

# Build output is in dist/ directory

2. Deploy to Server

Deploy the contents of dist/ directory to your web server (Nginx, Apache, CDN, etc.).

3. Configure Domain and HTTPS

# Nginx configuration example
server {
listen 80;
server_name your-domain.com;

# Redirect to HTTPS
return 301 https://$server_name$request_uri;
}

server {
listen 443 ssl;
server_name your-domain.com;

ssl_certificate /path/to/cert.pem;
ssl_certificate_key /path/to/key.pem;

root /path/to/dist;
index index.html;

location / {
try_files $uri $uri/ /index.html;
}
}

4. Configure API Address

Set production environment API address in project configuration:

// .env.production
VITE_API_BASE_URL=https://api.your-domain.com

Advantages

  • Fully Autonomous: Complete control over frontend and API
  • No CORS Issues: Same domain or CORS already configured
  • Best Performance: Direct access, no middleware
  • Production Ready: Suitable for production environment

Notes

  • Requires server resources and domain
  • Need to configure HTTPS certificate
  • Need to handle routing and static resources
  • Recommend using CDN to accelerate static resources

Solution Selection Recommendations

Choose the appropriate solution based on your scenario:

PhaseRecommended SolutionDescription
Local DevelopmentSolution 1: dev.lovrabet.comZero config, works out of box
Need Own API AccessSolution 2: Server CORSSimple and direct, good performance
Complex Business ScenariosSolution 3: Server ProxyFlexible and controllable, powerful
Production EnvironmentSolution 4: Independent DeploymentFully autonomous, best performance

FAQ

Q: Why doesn't using dev.lovrabet.com cause CORS issues?

A: Actually dev.lovrabet.com and api.lovrabet.com are still cross-origin (because domains are different). But dev.lovrabet.com has been added to the Lovrabet platform's CORS whitelist, and the server is configured to allow cross-origin requests from dev.lovrabet.com, so browsers don't block these requests, making it appear as if there's no CORS issue.

Q: Can I develop on local localhost?

A: Yes, but localhost is not in the CORS whitelist, accessing *.lovrabet.com APIs will have CORS issues. Recommend using dev.lovrabet.com for development.

Q: Must I deploy independently for production?

A: Not necessarily. If your frontend and API are under the same domain, or CORS is already configured, you can deploy directly. But independent deployment is usually more flexible and secure.

Q: Will server proxy affect performance?

A: There will be slight impact because it adds to the request chain. But for most applications, this impact is negligible. If you have very high performance requirements, recommend using Solution 2 or Solution 4.