본문 바로가기
코딩과 알고리즘

보안기능활성화 모드의 PHP + 몽고DB

지난 시간에는 몽고DB에서의 관리자 계정 설정에 대해서 다루어 보았습니다.

itadventure.tistory.com/381

 

몽고DB, 데이터베이스별 관리자 계정 생성

이번 시간에는 지난번의 몽고 DB 최고관리자 계정 생성에 이어, 데이터베이스별로 각각 관리자 아이디를 생성하는 방법을 알아보도록 하겠습니다. itadventure.tistory.com/380 몽고DB, 계정 보안! 최고

itadventure.tistory.com

특히 최고관리자 계정과 데이터베이스별 관리자 계정을 생성하고 패스워드를 설정하는 방법에 대해 살펴보았었는데요.

그러다 보니 원래 PHP 에서 잘되던 몽고DB 접속이 한가지 문제가 발생되었습니다.
PHP 에서 몽고 DB에 접속할 때 만일 몽고DB에 아이디, 패스워드가 걸려 있는 경우 아래와 같은 커넥션 문자열(Connection String)을 이용해야 합니다.

mongodb://계정:패스워드@localhost:27017/접속DB

PHP 에서는 아래와 같이 커넥션 문자열을 사용합니다.
아이디가 bookadmin, 패스워드는 ****, 접속권한DB는 craydb 인 셈이지요.

$manager = new MongoDB\Driver\Manager("mongodb://bookadmin:****@localhost:27017/craydb");

그런데 문제는 보안 설정으로 인해 몽고DB의 자료를 입력하거나 조회하는 기능을 실행하려고만 하면
아래와 같은 오류가 발생합니다.

The SCRAM_SHA_1 authentication mechanism requires libmongoc built with ENABLE_SSL 오류가 ...

이 것은 mongo.so 모듈에 SSL 모드가 활성화되지 않아서 생기는 문제인데요.
mongo.so 모듈에 SSL 모드를 활성화하려면 어떻게 해야 할까요?
openssl-devel 을 설치하고 mongo.so 모듈을 다시 컴파일을 해야 합니다.
그러면 알아서 활성화가 됩니다.

AWS 에서 아래 명령으로 root 계정으로 변경 후에

sudo su - root

yum 도구를 사용, openssl-devel  을 설치합니다.

yum install openssl-devel

이어서 pecl 명령으로 mongodb 모듈을 다시 컴파일합니다.

pecl install mongodb

그리고 나서 다시 서비스들을 재시작하면 되지요.

service nginx restart
service php-fpm restart
service mongod restart

이제 이 기반에서 작동되는 PHP 샘플코드를 공개합니다.
지난번에 몽고DB 콘솔에서 입력했던 학과 목록을 화면에 출력하는 소스인데요.
뭐 PHP에서 연결하는 부분에 샘플이니 소스 전체를 이해하시려는 부담은 가지지 않으셔도 됩니다.

첫번째는 몽고DB composer 확장모듈을 사용할 때입니다.
<style> 관련 소스는 화면을 좀 꾸미려고 한거니 크게 개의치 않으셔도 됩니다.
패스워드라고 적힌 부분은 지난번에 정하셨던 패스워드로 필히 변경해 주세요.
컬렉션명도 crayUniversity 가 아닌 경우 소스에서 해당 부분을 변경해 주시면 됩니다.

<style>
	.dtitle {
		font-size:15pt;
		text-decoration: underline;
		margin-bottom:20px;
	}
	.dcode {
		color:blue;
		border:1px solid blue;
		float:left;
		margin:0 4px 5px 0;
		padding: 1px;
	}
	.dname {
		color:black;
		border:1px dotted gray;
		float:left;
		margin:0 10px 5px 0;
		padding: 1px;
	}
</style>
<div class='dtitle'>크레이 대학교 학과목록</div>
<?php
  require 'vendor/autoload.php';  

	// 몽고 DB에 연결합니다.
  $con = new MongoDB\Client(
		"mongodb://uadmin:4321@localhost:27017/crayUniversity"); 	

  // craydb 데이터 베이스를 선택합니다.
  // 만약 데이터베이스가 없어도 데이터 삽입 단계에서 자동 생성됩니다.
  $db = $con->crayUniversity;
  // book 콜렉션을 선택합니다. 역시 컬렉션이 없어도 삽입 단계에서 자동 생성됩니다.
  // 입력한 정보를 검색합니다.
  foreach ($db->department->find() as $one) {  
    echo "<div class='dcode'>" . $one['code']. "</div>";
		echo "<div class='dname'>" . $one['name']. "</div>";
		echo "<div style='clear:both'></div>";
  }  
?>

출력결과

중요한 것은 이 부분만 체크해주시면 됩니다.
이 부분이 바로 몽고DB에 사용자 계정으로 접속하는 부분이거든요.

	// 몽고 DB에 연결합니다.
  $con = new MongoDB\Client("mongodb://uadmin:4321@localhost:27017/crayUniversity"); 	

두번째 소스 또한 동일한 기능을 하는 소스인데요.
composer 기반이 아닌, mongo.so 모듈을 다이렉트로 쓰는 소스입니다.
좀 더 내용이 복잡하지요. 

<style>
	.dtitle {
		font-size:15pt;
		text-decoration: underline;
		margin-bottom:20px;
	}
	.dcode {
		color:blue;
		border:1px solid blue;
		float:left;
		margin:0 4px 5px 0;
		padding: 1px;
	}
	.dname {
		color:black;
		border:1px dotted gray;
		float:left;
		margin:0 10px 5px 0;
		padding: 1px;
	}
</style>
<div class='dtitle'>크레이 대학교 학과목록</div>
<?php
	$manager = new MongoDB\Driver\Manager("mongodb://uadmin:패스워드@localhost:27017/crayUniversity");
	$cursor = $manager->executeQuery(
		"crayUniversity.department", 
		new MongoDB\Driver\Query([])
	);
	$rows = $cursor->toArray();
	foreach($rows as $one)
	{
		echo "<div class='dcode'>" . $one->code. "</div>";
		echo "<div class='dname'>" . $one->name. "</div>";
		echo "<div style='clear:both'></div>";
 	}
?>

이 소스에서도 몽고 DB에 연결하는 부분은 아래와 같습니다.

$manager = new MongoDB\Driver\Manager("mongodb://uadmin:패스워드@localhost:27017/crayUniversity");

PHP에서 위 2가지 방식중 몽고DB를 사용할 때는 어느쪽이 좋을까요?
양쪽 모두 장단점이 있는데요.

composer 확장 소스는 몽고DB 기본 함수를 이해하기 쉽게 한번 더 래핑(Rapping)한 것입니다.
그래서 의미적으로 이해가 되게 만들었지만 작동 속도는 느려지는 문제가 있습니다.
반면 개발 속도는 빠르겠지요. 이해가 빠르니까요? :)

반면 mongo.so 모듈의 기본 함수만을 이용한다면 의미적 이해에 대해서는 복잡한 부분이 있고,
개발에는 좀 더 시간이 소요되겠지만 사용자에게 빠른 속도를 제공할 수 있을 것입니다.
PHP 가 몽고DB gcc 모듈에게 다이렉트로 요청하는 셈이니까요.

여러분은 어떤 쪽을 선택하시렵니까? :)

필요하신 분에게 도움이 되셨는지요.
오늘도 여기까지 읽어주셔서 감사합니다.