为什么我只在 运行 GET 请求 onChange 时遇到 CORS 错误?
Why do I only encounter CORS error when running GET request onChange?
我正在使用 Create-React-App 客户端,在 package.json
中设置了 proxy: "localhost:5000
,以便在我们的 Node.js 服务器上轻松查询 API。
我正在尝试通过以下函数使用 HERE 的自动完成功能API。
自动完成功能:
import axios from 'axios';
import hereKeys from '../config/hereConfig';
export const autoCompleteFullAddress = async query => {
let address = null;
try {
await axios
.get('https://autocomplete.geocoder.api.here.com/6.2/suggest.json', {
params: {
app_id: hereKeys.appId,
app_code: hereKeys.appCode,
query: query,
maxresults: 1,
},
})
.then(response => {
address = response.data.suggestions[0].address;
});
} finally {
return address;
}
};
我在呈现的组件中有一个辅助函数,可以根据用户在输入字段中的输入来执行此操作。
输入组件:
const [puAddress, setPuAddress] = useState('');
const [puQuery, setPuQuery] = useState('');
const onAddressInput = e => {
const query = e.target.value;
// This Fails
autoCompleteFullAddress(query).then(suggestion => {
setPuQuery(query);
console.log(suggestion);
});
};
// This works
autoCompleteFullAddress('37044 Even Lane').then(suggestion => {
console.log(suggestion);
});
return (
<TextField
value={puQuery}
onChange={e => onAddressInput(e)}
/>
);
当 autoCompleteFullAddress
独立运行时,它 console.log
是正确的输出。但是一旦我尝试在组件的更改上执行它,它就会失败并引发错误。
抛出错误:
Access to XMLHttpRequest at 'https://autocomplete.geocoder.api.here.com/6.2/suggest.json?
app_id=REDACTED&app_code=REDACTED&query=Elm+St&maxresults=1'
from origin 'http://localhost:3000' has been blocked by CORS policy:
Response to preflight request doesn't pass access control check:
It does not have HTTP ok status.
和:
OPTIONS https://autocomplete.geocoder.api.here.com/6.2/suggest.json?
app_id=REDACTED&app_code=REDACTED&query=Elm+St&maxresults=1 405
请求失败Headers:
Access-Control-Request-Headers: authorization
Access-Control-Request-Method: GET
Origin: http://localhost:3000
Referer: http://localhost:3000/pricing-tool
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.169 Safari/537.36
请求成功Headers:
Accept: application/json, text/plain, */*
Origin: http://localhost:3000
Referer: http://localhost:3000/pricing-tool
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.169 Safari/537.36
对于将来可能会像这样设置访问令牌以便向您的 API 发出请求的人。问题是它试图在所有 Axios 请求上发送带有令牌的 Auth header。
import axios from 'axios';
const setAuthToken = token => {
if (token) {
const bearerToken = 'Bearer ' + token;
// Apply to every request
axios.defaults.headers.common['Authorization'] = bearerToken;
} else {
// Delete auth header
delete axios.defaults.headers.common['Authorization'];
}
};
export default setAuthToken;
可以通过更改逻辑或简单地使用外部 API 的提取来修复。
我修复了根据该特定请求删除 header 的问题。
import axios from 'axios';
import hereKeys from '../config/hereConfig';
export const autoCompleteFullAddress = async query => {
let address = null;
delete axios.defaults.headers.common['Authorization'];
try {
await axios
.get('https://autocomplete.geocoder.api.here.com/6.2/suggest.json', {
crossdomain: true,
params: {
app_id: hereKeys.appId,
app_code: hereKeys.appCode,
query: query,
maxresults: 1,
country: 'USA,MEX,CAN',
},
})
.then(response => {
address = response.data.suggestions[0].address;
});
} finally {
return address;
}
};
我正在使用 Create-React-App 客户端,在 package.json
中设置了 proxy: "localhost:5000
,以便在我们的 Node.js 服务器上轻松查询 API。
我正在尝试通过以下函数使用 HERE 的自动完成功能API。
自动完成功能:
import axios from 'axios';
import hereKeys from '../config/hereConfig';
export const autoCompleteFullAddress = async query => {
let address = null;
try {
await axios
.get('https://autocomplete.geocoder.api.here.com/6.2/suggest.json', {
params: {
app_id: hereKeys.appId,
app_code: hereKeys.appCode,
query: query,
maxresults: 1,
},
})
.then(response => {
address = response.data.suggestions[0].address;
});
} finally {
return address;
}
};
我在呈现的组件中有一个辅助函数,可以根据用户在输入字段中的输入来执行此操作。
输入组件:
const [puAddress, setPuAddress] = useState('');
const [puQuery, setPuQuery] = useState('');
const onAddressInput = e => {
const query = e.target.value;
// This Fails
autoCompleteFullAddress(query).then(suggestion => {
setPuQuery(query);
console.log(suggestion);
});
};
// This works
autoCompleteFullAddress('37044 Even Lane').then(suggestion => {
console.log(suggestion);
});
return (
<TextField
value={puQuery}
onChange={e => onAddressInput(e)}
/>
);
当 autoCompleteFullAddress
独立运行时,它 console.log
是正确的输出。但是一旦我尝试在组件的更改上执行它,它就会失败并引发错误。
抛出错误:
Access to XMLHttpRequest at 'https://autocomplete.geocoder.api.here.com/6.2/suggest.json?
app_id=REDACTED&app_code=REDACTED&query=Elm+St&maxresults=1'
from origin 'http://localhost:3000' has been blocked by CORS policy:
Response to preflight request doesn't pass access control check:
It does not have HTTP ok status.
和:
OPTIONS https://autocomplete.geocoder.api.here.com/6.2/suggest.json?
app_id=REDACTED&app_code=REDACTED&query=Elm+St&maxresults=1 405
请求失败Headers:
Access-Control-Request-Headers: authorization
Access-Control-Request-Method: GET
Origin: http://localhost:3000
Referer: http://localhost:3000/pricing-tool
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.169 Safari/537.36
请求成功Headers:
Accept: application/json, text/plain, */*
Origin: http://localhost:3000
Referer: http://localhost:3000/pricing-tool
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.169 Safari/537.36
对于将来可能会像这样设置访问令牌以便向您的 API 发出请求的人。问题是它试图在所有 Axios 请求上发送带有令牌的 Auth header。
import axios from 'axios';
const setAuthToken = token => {
if (token) {
const bearerToken = 'Bearer ' + token;
// Apply to every request
axios.defaults.headers.common['Authorization'] = bearerToken;
} else {
// Delete auth header
delete axios.defaults.headers.common['Authorization'];
}
};
export default setAuthToken;
可以通过更改逻辑或简单地使用外部 API 的提取来修复。
我修复了根据该特定请求删除 header 的问题。
import axios from 'axios';
import hereKeys from '../config/hereConfig';
export const autoCompleteFullAddress = async query => {
let address = null;
delete axios.defaults.headers.common['Authorization'];
try {
await axios
.get('https://autocomplete.geocoder.api.here.com/6.2/suggest.json', {
crossdomain: true,
params: {
app_id: hereKeys.appId,
app_code: hereKeys.appCode,
query: query,
maxresults: 1,
country: 'USA,MEX,CAN',
},
})
.then(response => {
address = response.data.suggestions[0].address;
});
} finally {
return address;
}
};