오늘 새벽 변경사항 이후로 지도 이미지를 못 가져와요

오늘 새벽 변경사항 이후로 지도 이미지를 못 가져와요
스카이뷰 쪽은 문제 없구요

[마커는 나오는데 지도 화면이 안나옵니다] 글의 사용자님과 동일한 문제 이고요

공지사항 댓글에 ddochi님이 얘기한 것과도 동일한 문제입니다

@matchaicecream

사용하시는 앱키가 등록된 계정으로 문의 부탁드립니다.

구현된 페이지를 확인할 수 있는 주소가 있으면 알려주시고,
https://map.kakao.com/ 서비스 접속 시 어떤 지도 함께 알려주세요.

앱키가 등록된 계정으로 재문의 드립니다.
구현된 페이지 주소는 https://kr.gcrmportal.com 이고, 저희 내부 계정으로 로그인 상태에서만 접속을 허용해둔 사이트라서 카카오측에서 확인은 안 되실것 같아서 지도는 파란화면으로만 나오는 화면 내용을 캡처해서 첨부했습니다.
*스카이뷰는 정상적으로 조회가 되어 네트워크나 방화벽 이슈는 아닌 것 같습니다.

지도 타일, copyright, 컨트롤러, 마커 이미지를 보면 현재 제공하는 버전이 아닌
이전 버전을 호출해서 사용하고 있는 걸로 보입니다.

먼저 지도 웹 SDK import하는 부분 다시 한번 확인 부탁드립니다.
아래 주소 이외에 https://t1.daumcdn.net 등 카카오맵 관련 다른 도메인의 js 를 별도로 호출하는 부분이 있다면 제거 부탁드립니다.

<script type="text/javascript" src="//dapi.kakao.com/v2/maps/sdk.js?appkey=발급받은 APP KEY를 넣으시면 됩니다."></script>

@misothe1004

첨부해주신 화면을 보니
당사의 API 를 가이드대로 호출하시지 않았으며
그와 같은 호출은 제재 대상입니다.

https://apis.map.kakao.com/web/guide/

가이드에 안내된 방법으로만 사용하셔야 하며,
직접적인 타일 이미지의 접근 또는 가이드 하지 않은 별도의 js 등을 호출하시면 안됩니다.

관련 코드 수정과 수정 이후 정상적으로 구현된 화면을 남겨주시길 요청드립니다.

s1.daumcdn.net 호출부를 제거하였습니다.

<jsInclude>//s1.daumcdn.net/svc/attach/U03/cssjs/mapapi/3.5.14/1484818226526/open.js</jsInclude>

남아있는 부분은 이렇게 호출하고 있습니다

<jsInclude>//dapi.kakao.com/v2/maps/sdk.js?appkey=앱키</jsInclude>

그런데 이제는 아래와 같은 에러가 발생하는데요. 가이드주실수있을까요?
sap-ui-m-zen.js:88 2023-07-26 13:19:27.322699 A JavaScript error occurred. daum.maps.Circle is not a constructor TypeError: daum.maps.Circle is not a constructor at n.

오류 메세지를 보면 Circle 생성자가 없어서 나는 오류로 보입니다.
스크립트가 로드되기 전에 Circle객체에 접근한건 아닌지 확인 부탁드립니다.
그리고 추가 문의하실 경우 현상을 확인할 수 있는 코드 또는 외부 URL 첨부 부탁드립니다.

dapi.kakao.com 에서 daum.maps.Circle 를 사용할 수는 있다는 말씀이시죠?

지금 코드 모양은 daum.maps.Circle 접근하는 코드는 res폴더 안에 있고
dapi.kakao.com호출은 contribution.xml안에 있는 상태입니다.
res폴더와 contribution.xml은 같은 레벨에 들어 있습니다

네 예제 페이지에서도 도형 예제가 정상 동작하고 있습니다.
https://apis.map.kakao.com/web/sample/drawShape/

추측하기로는 sdk가 로드되기 전에 kakao.maps.Circle 객체를 생성해서 생긴 문제로 보입니다.
코드 실행 순서를 확인해주세요.
실행 코드보다 스크립트가 먼저 로드되어야 합니다.

		<jsInclude>//dapi.kakao.com/v2/maps/sdk.js?appkey=앱키</jsInclude>
		
		<jsInclude>res/js/component.js</jsInclude>

저도 순서가 의심스럽긴 했는데
contribution.xml 안에서 js include 써진 순서가 이렇게 되어 있습니다
dapi 가 먼저 써져 있고 그 다음에 component.js 가 쓰여져 있어요
component.js 안에 daum.maps.Circle 접근하는 코드가 있습니다.

<sdkExtension 다음에 <group title 다음에 <component id 다음이 //dapi.kakao.com/v2/maps/sdk.js?appkey= 로 거의 최상단에 있습니다…

이렇게 되면 스크립트가 먼저 로드 되고 그 다음에 실행 코드가 로드 되는거로 이해를 했는데 혹시 아니라면 알려주실 수 있을까요?

브라우저에서 스크립트를 다운받기 때문에 시간이 길어지면 로컬 파일이 먼저 실행될 수 있습니다.
sdk.js, kakao.js 로드 전에 로컬 파일이 먼저 실행되는지 네트워크 탭으로 확인해주세요.

그리고 스크립트를 동적으로 로드하는 방식도 제공하고 있습니다.
스크립트 로드가 끝난 후 콜백함수에서 지도에 필요한 동작을 실행할 수 있게 구현하는 방법도 있으니 문서 참고해주세요.
https://apis.map.kakao.com/web/documentation/#load_load

소스레벨에서 어떻게 정의되어 있는가보다,
브라우저(크롬 추천)의 개발자도구의 네트워크 탭을 통해서,
실제 로딩이 어떻게 되는가,

즉 말씀하신 jsInclude를 통한 스크립트 인젝션이, 최종 파싱되서 HTML파일로 만들어졌을때의, 실제 브라우저에서 어떤방식으로 파일을 받고 있는가가 중요합니다.

이 부분을 브라우저에서 확인을 해보시는게 좋을 것 같습니다. 이에 따른 스크린샷도 주시면 좋구요.

안녕하세요,

제가 이쪽을 잘 몰라서 하나하나 여쭤보는 점 죄송합니다 ㅠㅠ!!

먼저 이런식으로 defer 사용해보려고 했는데

  <script src="https://dapi.kakao.com/v2/maps/sdk.js?appkey=myappkey" defer onload="sdkLoadedCallback()"></script>

xml에서는 이런식으로 사용할수 없더라구요.

아래는 관련해서 chatgpt 알려준 내용인데 요약하자면 비동기 신경 안 쓰고 개발해도 된다고 하는데 이슈가 있는 상태 입니다.

In SAP Design Studio, when you specify elements in the contribution.xml file, the specified JavaScript files are included in the application, but their loading behavior is determined by the way the browser handles script loading (synchronously or asynchronously).If you are using the SAP Design Studio SDK to develop custom components, the code inside your component.js file will execute in the context of the application when the application is run. At that point, the JavaScript files included via elements will have already been loaded, and any JavaScript code in the component.js file can safely access the objects from the loaded scripts, including the Kakao Maps SDK.In other words, when you develop custom components using the SAP Design Studio SDK, you don’t need to worry about handling asynchronous script loading within the component.js file. The SDK takes care of loading the required scripts before your component’s code executes.To summarize, if you are using the SAP Design Studio SDK and have specified the Kakao Maps SDK using a in the contribution.xml file, you can directly use the daum.maps.Circle and other objects from the SDK in your component.js file without any additional handling for asynchronous loading.

우선, 네트워크 탭에서 확인 시 component.js?version=(난수값)이 sdk.js?appkey=(앱키)부분 보다 위에 적혀 있는 것으로 보여서(?)(제가 잘 몰라서 잘못 분석한 것일수도 있습니다), component.js를 다음과 같은 3가지 방법으로 수정을 했지만 결과적으로는 3가지 모두 실패한 상태입니다.

  1. component.js 안에 쓰여 있던 전체 코드를
    window.onload = function() { 안에 집어 넣기
  2. component.js의 전체 코드를
    kakao.maps.load(function() { 안에 집어 넣기
  3. component.js 파일의 맨 첫 부분에 아래의 코드 넣어주었습니다.
function loadKakaoMapsSDK() {
  var kakaoMapsAPIKey = '앱키';

  // Create a new script element
  var scriptElement = document.createElement('script');

  // Set the source URL for the Kakao Maps SDK with the API key
  scriptElement.src = '//dapi.kakao.com/v2/maps/sdk.js?appkey=' + kakaoMapsAPIKey;

  // Append the script element to the <head> or <body> of your HTML document
  document.head.appendChild(scriptElement);
}

loadKakaoMapsSDK();

첫번째와 두번째 방법을 했을 때에는
커스텀 코드는 뜨는데 지도 쪽을 (스카이뷰 포함) 모두 불러오지 못했고

세번째 방법을 했을 때는
아예 하얀색 빈 화면으로 뜨면서 커스텀 코드들도 뜨지 않았습니다.

현재 보이는 상태는 3번째 방법으로 적용해서 빈 화면으로 보이는 상태입니다.

image

네트워크 콘솔 캡쳐에서 이미지 올리고 싶었는데
업로드 에러가 나서 일단 에러메시지 첨부하였습니다…
네트워크 콘솔에 나오는 에러 메시지는 다음과 같습니다.

sap-ui-m-zen.js:88 2023-07-27 15:49:25.526800 A JavaScript error occurred. daum.maps.Circle is not a constructor TypeError: daum.maps.Circle is not a constructor at n. (https://stg-kr.gcrmportal.com/BOE/portal/2304261226/LumiraWebApp/zen/mimes/sdk_include/com.pnt.gcrm.map/res/js/component.js?version=7BE1F284933CF2A0DB5FA2935D4B722B:68:21) at new n (https://stg-kr.gcrmportal.com/BOE/portal/2304261226/LumiraWebApp/zen/mimes/combined_static_includes_1.js?version=20220923164746:52:96512) at f.storeProperties (https://stg-kr.gcrmportal.com/BOE/portal/2304261226/LumiraWebApp/zen/mimes/combined_static_includes_1.js?version=20220923164746:52:512648) at a.create (https://stg-kr.gcrmportal.com/BOE/portal/2304261226/LumiraWebApp/zen/mimes/combined_static_includes_1.js?version=20220923164746:52:492003) at a.createAndAdd (https://stg-kr.gcrmportal.com/BOE/portal/2304261226/LumiraWebApp/zen/mimes/combined_static_includes_1.js?version=20220923164746:52:138156) at G (https://stg-kr.gcrmportal.com/BOE/portal/2304261226/LumiraWebApp/zen/mimes/combined_static_includes_1.js?version=20220923164746:52:119708) at sap.zen.Dispatcher.dispatchCreateControl (https://stg-kr.gcrmportal.com/BOE/portal/2304261226/LumiraWebApp/zen/mimes/combined_static_includes_1.js?version=20220923164746:52:117868) at AbsoluteLayoutHandler.updateChildren (https://stg-kr.gcrmportal.com/BOE/portal/2304261226/LumiraWebApp/zen/mimes/combined_static_includes_1.js?version=20220923164746:52:138800) at init (https://stg-kr.gcrmportal.com/BOE/portal/2304261226/LumiraWebApp/zen/mimes/combined_static_includes_1.js?version=20220923164746:52:327250) at AbsoluteLayoutHandler.createAndAdd (https://stg-kr.gcrmportal.com/BOE/portal/2304261226/LumiraWebApp/zen/mimes/combined_static_includes_1.js?version=20220923164746:52:329951) -

그리고 위에서 lea.ju 님께서 확인해주시긴 했는데 의심스러워서
kakao.maps.Circle으로 바꾸었더니 에러메시지에 kakao.maps.Circle으로 나올뿐 메시지가 동일했습니다 ㅎㅎㅎ ㅠㅠ

2023-07-27 17:05:42.671300 A JavaScript error occurred. kakao.maps.Circle is not a constructor TypeError: kakao.maps.Circle is not a constructor at n. (https://stg-kr.gcrmportal.com/BOE/portal/2304261226/LumiraWebApp/zen/mimes/sdk_include/com.pnt.gcrm.map/res/js/component.js?version=6AD6F9B2605BADAF21D997E20AD9D134:68:21) at new n

지도 SDK의 경우 이 실행 순서가 보장되어야 합니다.

  1. sdk 로딩 (무조건 최우선 순위 로딩 필요)
  2. kakao.js 로딩 (코어파일, sdk에서 자동 로딩)
  3. 그외 사용자 코드 실행

현재 위에 적어주신내용을 보면 compoent.js가
sdk로딩보다 먼저 실행되므로 당연히 오류가 발생하는 것인데;

제가 적은 순서에서,

2번 3번의 경우에는

3번 사용자코드를 kakao.maps.load(function() {}) 으로 묶어 주신다면,
2번이 로딩되기 전에 실행되더라도 괜찮습니다. 왜냐하면 sdk에서 2번을 로딩한 다음에 3번을 실행시키거든요.

다만 이외 별개로 sdk는 무조건 1번으로 다운을 먼저 받아야 합니다.
이는 sdk가 받아지면서, 기본적인 지도SDK의 실행 환경이 만들어 지기 때문에 그렇습니다.
1번이 실행이 안된 상태에는 kakao.maps.load라는 함수자체가 없어서 여기서 오류가 발생하기 되기 때문입니다.

그래서 해결방법은 현재 SDK에서도 동기성을 보장하기 위해서 사용하고 있는 document.write를 사용하는 것입니다.
개인적으로는 이 방법은 UI를 멈추게 하기 때문에, 수행시간이 긴 로직에서 사용하면 먹통이 되는 현상이 발생되기에 그렇게 추천드리진 않습니다만,(크롬에서도 이러한 이유로 경고를 띄웁니다) 특정 목적에 맞게는 사용하면 문제 없습니다.

즉 위에 말씀하신 내용에서

component.js의 전체 코드를
kakao.maps.load(function() { 안에 집어 넣기

이렇게 해주고,
component.js의 파일 맨 첫 부분에

var kakaoMapsAPIKey = 'appkey';
document.write('<script type="text/javascript" src="//dapi.kakao.com/v2/maps/sdk.js?appkey=' + kakaoMapsAPIKey + '&libraries=services"><\/script>');

이렇게 작성해 주시면 실행 순서가 보장될 것으로 보입니다.

한번 참고해 주세요~

추가) 올려주신 코드에서 script태그를 생성해서 하는 방법과 비슷해보이나, script태그 생성후 body에 넣는것은, 이렇게 해도 sdk는 다운로드가 되나 브라우저 자체에서 비동기로 이루어지기 때문에, 효과가 없습니다. 이와 반대로 document.write는 실행할때 UI쓰레드와 동기적으로 동작하기에, document.write에 작성된 코드가 다 다운받고 실행되기 전에는, 이 코드 아랫부분이 실행되지 않습니다. 그래서 화면이 멈추는 것이죠. 다만 지도sdk 파일의 경우 그 용량과 로직이 매우 단순해서, 멈춘지도 모르게 지나가므로 괜찮습니다. 실행을 오래해야 하는 특정 로직들은 이렇게 실행하면 안되구요.

goni.r님 께서 알려주신대로 수정한 이후에는 노란색으로 워닝 발생하던 Failed to execute ‘write’ on ‘Document’ 에러 메시지가 1개 에서 2개로 바뀌었습니다.

sdk.js?appkey=앱키 Failed to execute ‘write’ on ‘Document’: It isn’t possible to write into a document from an asynchronously-loaded external script unless it is explicitly opened.

아래쪽에 A JavaScript error occurred. kakao.maps.Circle is not a constructor TypeError: kakao.maps.Circle is not a constructor at 에러메시지도 여전히 발생을 하구요.

그리고 오 kakao.maps.Map이 없어서 뭐지 했는데 글과 Kakao 지도 Web API Documentation 참고해서 dapi.kakao.com 호출부에 autoload=false 파라메터 추가 해보았는데 파라메터 추가하는것으로는 해결이 되지 않은 상태입니다

안녕하세요~

네. 해당 내용 확인해 봤습니다.

기본적으로 지도SDK는 내부에서 document.write를 사용하고 있습니다.(이는 여러 환경적인 이슈때문에 그러한 것이긴 합니다)
이는 보통 문제가 발생되진 않는데, 여러 프레임워크들과 결합해서 소프트웨어가 구성되는 경우엔 문제가 발생하기도 합니다. 각자 실행 환경이 다르니까요. (document.write의 오류 관련해서 구글링이나 gpt검색을 해보시면 아실 수 있습니다)
그래서 만들어 둔게 autoload=false인데, 이 파라미터를 sdk.js 뒤에 추가를 하게되면 (sdk.js?autoload=false)
document.write를 사용하지 않으며, sdk는 기본적인 kakao.maps와 같은 네임스페이스를 비롯하여 기본 환경만 설정을 하게 됩니다.
그 이후에 kakao.maps.load함수가 실행되면, 실제 core스크립트를 로딩하게 되며, 코어스크립트가 로딩된 이후에
load함수의 콜백함수에 정의된 코드를 실행하게 됩니다.

kakao.maps.Circle is not a constructor 라는 오류도, kakao.maps 라는 네임스페이스는 만들어 졌는데(sdk.js 파일은 정상 다운이 됬다는 말) core스크립트가 로딩이 되지 않아 maps가 비어 있어 Circle이 없어서 발생하는 이슈입니다.
그렇기에 이 Circle 을 비롯하여 모든 maps관련된 코드들은 kakao.maps.load 함수의 콜백함수로 묶어서 실행해 주시기 바랍니다.

<script type="text/javascript" src="//dapi.kakao.com/v2/maps/sdk.js?appkey=keystring&autoload=false&libraries=services"><\/script>

<script>
kakao.maps.load(function() {
    new kakao.maps.Circle(); .......... //이렇게;;
});
</script>

아 네임스페이스는 daum.maps던, kakao.maps던 2개다 지원하니 참고바랍니다. daum은 레거시 대응으로 남겨둔것이라 보시면 됩니다.

아무튼 이렇게 실행이 보장되도록 코드 구성을 해보시면 감사하겠습니다.

현재 개발중인 소프트웨어가 일반 브라우저에서 실행되는지, 또는 특정 플랫폼 위에서 실행되는지 알 수는 없지만;
일반 브라우저에서는 위처럼 하면 아무 문제없이 실행이 됩니다.
특정 플랫폼 관련해서는 해당 플랫폼의 다큐멘테이션이나 이런 부분 참고해서, 오류를 확인해 보시는게 좋을 것 같습니다.

감사합니다.