728x90
반응형

PC 같은 환경에서는 hosts 파일을 수정해서 특정 아이피를 원하는 도메인으로 설정하여 사용할 수 있는데

스마트폰이나 태블릿 같은 경우엔 이렇게 사용하는 것이 어려웠다.

 

그래서 내부망에서 설정한 도메인으로 접속할 수 있는 방법이 없을까하고 찾아보던 중 dnsmasq 라는 것을 발견했다.

$ brew install dnsmasq

/usr/local/etc/dnsmasq.conf에서 다음과 같이 추가한다.

#port=5353
port=53
...

#address=/double-click.net/127.0.0.1
address=/my.domain/127.0.0.1

/etc/hosts에 다음과 같이 추가한다.

192.168.xxx.xxx	test.my.domain	my-local

그리고 dnsmasq를 시작 또는 재시작하면 되는데 dnsmasq 시작과 종료는 다음과 같이 하면 된다.

$ sudo brew services stop dnsmasq
$ sudo brew services start dnsmasq

스마트폰이나 태블릿에서 접속할 때 DNS 서버를 dnsmasq가 설치된 PC의 아이피를 넣으면 된다.

 

마지막으로 맥에서 웹 서버를 띄운 다음 test.my.domain으로 접속되는지 확인하면 된다.

 

참고 문헌

  1. https://davebaker.me/2014/11/26/setting-up-local-dns-server-on-osx/

  2. https://st03k.tistory.com/entry/Micro-Service-추천-dnsmasq-hosts-파일로-DNS-구축하기

  3. https://www.joinc.co.kr/w/Site/System_management/Dnsmasq

  4. https://ghj1001020.tistory.com/769

반응형
728x90
반응형

Jenkins에서 k8s로 배포하기 위해 Kubernetes Continuous Deploy 라는 플러그인을 사용하고 있었다.

 

그런데 최신으로 업데이트를 하고 난 뒤 다음과 같은 에러가 발생했다.

ERROR: ERROR: Can't construct a java object for tag:yaml.org,2002:io.kubernetes.client.openapi.models.V1Deployment; exception=Class not found: io.kubernetes.client.openapi.models.V1Deployment
 in 'reader', line 1, column 1:
    apiVersion: apps/v1
    ^

hudson.remoting.ProxyException: Can't construct a java object for tag:yaml.org,2002:io.kubernetes.client.openapi.models.V1Deployment; exception=Class not found: io.kubernetes.client.openapi.models.V1Deployment
 in 'reader', line 1, column 1:
    apiVersion: apps/v1
    ^

	at org.yaml.snakeyaml.constructor.Constructor$ConstructYamlObject.construct(Constructor.java:335)
	at org.yaml.snakeyaml.constructor.BaseConstructor.constructObjectNoCheck(BaseConstructor.java:229)
	at org.yaml.snakeyaml.constructor.BaseConstructor.constructObject(BaseConstructor.java:219)
	at io.kubernetes.client.util.Yaml$CustomConstructor.constructObject(Yaml.java:337)
	at org.yaml.snakeyaml.constructor.BaseConstructor.constructDocument(BaseConstructor.java:173)
	at org.yaml.snakeyaml.constructor.BaseConstructor.getSingleData(BaseConstructor.java:157)
	at org.yaml.snakeyaml.Yaml.loadFromReader(Yaml.java:490)
	at org.yaml.snakeyaml.Yaml.loadAs(Yaml.java:456)
	at io.kubernetes.client.util.Yaml.loadAs(Yaml.java:224)
	at io.kubernetes.client.util.Yaml.modelMapper(Yaml.java:494)
	at io.kubernetes.client.util.Yaml.loadAll(Yaml.java:272)
	at com.microsoft.jenkins.kubernetes.wrapper.KubernetesClientWrapper.apply(KubernetesClientWrapper.java:236)
	at com.microsoft.jenkins.kubernetes.command.DeploymentCommand$DeploymentTask.doCall(DeploymentCommand.java:172)
	at com.microsoft.jenkins.kubernetes.command.DeploymentCommand$DeploymentTask.call(DeploymentCommand.java:124)
	at com.microsoft.jenkins.kubernetes.command.DeploymentCommand$DeploymentTask.call(DeploymentCommand.java:106)
	at hudson.FilePath.act(FilePath.java:1163)
	at com.microsoft.jenkins.kubernetes.command.DeploymentCommand.execute(DeploymentCommand.java:68)
	at com.microsoft.jenkins.kubernetes.command.DeploymentCommand.execute(DeploymentCommand.java:45)
	at com.microsoft.jenkins.azurecommons.command.CommandService.runCommand(CommandService.java:88)
	at com.microsoft.jenkins.azurecommons.command.CommandService.execute(CommandService.java:96)
	at com.microsoft.jenkins.azurecommons.command.CommandService.executeCommands(CommandService.java:75)
	at com.microsoft.jenkins.azurecommons.command.BaseCommandContext.executeCommands(BaseCommandContext.java:77)
	at com.microsoft.jenkins.kubernetes.KubernetesDeploy.perform(KubernetesDeploy.java:42)
	at jenkins.tasks.SimpleBuildStep.perform(SimpleBuildStep.java:112)
	at hudson.tasks.BuildStepCompatibilityLayer.perform(BuildStepCompatibilityLayer.java:78)
	at hudson.tasks.BuildStepMonitor$1.perform(BuildStepMonitor.java:20)
	at hudson.model.AbstractBuild$AbstractBuildExecution.perform(AbstractBuild.java:741)
	at hudson.model.Build$BuildExecution.build(Build.java:206)
	at hudson.model.Build$BuildExecution.doRun(Build.java:163)
	at hudson.model.AbstractBuild$AbstractBuildExecution.run(AbstractBuild.java:504)
	at hudson.model.Run.execute(Run.java:1894)
	at hudson.model.FreeStyleBuild.run(FreeStyleBuild.java:43)
	at hudson.model.ResourceController.execute(ResourceController.java:97)
	at hudson.model.Executor.run(Executor.java:428)
Caused by: hudson.remoting.ProxyException: org.yaml.snakeyaml.error.YAMLException: Class not found: io.kubernetes.client.openapi.models.V1Deployment
	at org.yaml.snakeyaml.constructor.Constructor.getClassForNode(Constructor.java:664)
	at org.yaml.snakeyaml.constructor.Constructor$ConstructYamlObject.getConstructor(Constructor.java:322)
	at org.yaml.snakeyaml.constructor.Constructor$ConstructYamlObject.construct(Constructor.java:331)
	... 33 more
ERROR: Kubernetes deployment ended with HasError

해당 플러그인 깃헙 이슈에서 찾아보니 다운그레이드를 하면 된다고 했지만

 

막상 시도를 해보니 의존성으로 인하여 모든 플러그인들을 다운그레이드를 해야했다.

 

그래서 다른 방법을 찾다가 Jackson 2 API에서 snakeyaml 에 대한 의존성을 추가해서 발생한 문제라는 것을 알게되었다.

 

이를 해결하기 위해 다음 부분을 주석하여 빌드한 뒤 jenkins에 설치해보니 에러없이 잘 동작하는 것을 확인할 수 있었다.

 

github.com/jenkinsci/jackson2-api-plugin/blob/master/pom.xml#L149-L164

...
    <dependency>
      <groupId>com.fasterxml.jackson.dataformat</groupId>
      <artifactId>jackson-dataformat-yaml</artifactId>
      <version>${jackson.version}</version>
      <exclusions>
        <exclusion>
          <groupId>org.yaml</groupId>
          <artifactId>snakeyaml</artifactId>
        </exclusion>
      </exclusions>
    </dependency>

    <dependency>
      <groupId>io.jenkins.plugins</groupId>
      <artifactId>snakeyaml-api</artifactId>
    </dependency>
 ...

 

참고 문헌

  1. plugins.jenkins.io/kubernetes-cd/

  2. https://github.com/jenkinsci/kubernetes-cd-plugin/issues/134

  3. https://github.com/jenkinsci/jackson2-api-plugin

반응형
728x90
반응형

저번에 해결이 된 줄 알고 좋아했지만 곧 정책 위반으로 삭제가 됐다.

 

이번엔 확실히 해결하기 위해 더 가열차게 검색을 하여 찾아봤다.

 

React Native의 라이프 사이클을 다시 한번 확인했다.

 

 

앱이 로딩되는 중에 광고를 가져오면 안된다고 하여 어느 시점에 해야하는지 살펴봤다.

 

기존에는 constructor에서 호출하고 있었고 setTimeout으로 했지만 

 

아직 앱이 로딩 중이기에 구글에서 위반이라고 판단한 것 같았다.

 

그래서 확실하게 componentDidMount에서 호출하여 광고를 가져오도록 했다.

 

그리고 앱 시작하고 스플래시 화면 다음에 전면 광고가 나오도록 했는데

 

광고를 가져오는 시점이 변경되어 광고가 나오는 시점도 변경했다.

 

2주 정도 지난 현재까지 위반 메일이 오지않는 것으로 봐서 해결된 것 같다.

 

참고 문헌

  1. https://projects.wojtekmaj.pl/react-lifecycle-methods-diagram/

  2. https://support.google.com/admob/answer/6201362?ref_topic=2745287

반응형
728x90
반응형

서버를 구성하는데 mediainfoffmpeg을 설치할 필요가 있었다.

 

설치할 서버가 적을 경우 하나씩 해도 되지만 서버가 많을 경우 일일이 하는 것이 어렵다.

 

이를 쉽게 하기 위해 자동화 도구 중에 하나인 Ansible을 사용했다.

 

많은 명령어들을 지원하는데 yum으로만 진행하여 다음과 같이 설정 파일을 만들었다.

- hosts: "{{ host }}"
  tasks:
  - name: install epel-release
    yum:
      name: epel-release
      state: present
    become: yes
    become_user: root
  - name: localinstall rpmfusion-free-release-7
    yum:
      name: https://download1.rpmfusion.org/free/el/rpmfusion-free-release-7.noarch.rpm
      disable_gpg_check: yes
      state: present
    become: yes
    become_user: root
  - name: install mediainfo
    yum:
      name: mediainfo
      state: present
    become: yes
    become_user: root
  - name: install ffmpeg
    yum:
      name: ffmpeg
      state: present
    become: yes
    become_user: root

stateyum과 같이 사용하는 값인데 absent, installed, latest, present, removed이 있다.

 

present, installed, latest는 설치를 진행하고 absent, removed는 패키지를 제거한다.

 

becomebecome_user를 사용하여 사용자를 전환할 수 있으며 become_userroot가 기본값이다.

 

yum 프록시 설정이 필요한 경우 yum.conf를 수정해야하는데 lineinfile을 사용하여 쉽게 수정할 수 있다.

 

- hosts: "{{ host }}"
  tasks:
 - name: proxy added to /etc/yum.conf
    lineinfile:
      path: /etc/yum.conf
      regexp: 'proxy='
      insertafter: '\[main\]'
      line: 'proxy=proxy_addr'
      state: present
    become: yes
    become_user: root

regexp는 찾으려는 문자열의 정규식이며 insertafter에 해당 문자열 다음에

 

statepresent인 경우 line의 값을 추가한다.

 

stateabsent, present가 있는데 absentline을 제거하고 present는 추가한다.

 

참고 문헌

  1. https://linuxize.com/post/how-to-install-ffmpeg-on-centos-7/

  2. https://docs.ansible.com/ansible/latest/modules/yum_module.html

  3. https://docs.ansible.com/ansible/latest/modules/lineinfile_module.html

반응형

+ Recent posts