728x90
고객의 동의없이 수집한 개인정보를 텔레마케팅 업체에 등 무단 제공하고 해지신청 고객의 개인정보까지도 불법 사용한 혐의로 하나로텔레콤 전현직 간부들이 대거 형사처벌을 받게 됐다.

서울지방경찰청 사이버범죄수사대는 23일 고객정보를 은행이나 텔레마케팅회사에 불법 제공한 혐의(정보통신망법 위반)로 하나로텔레콤 박병무 전 대표(47)와 전현직 지사장 22명을 불구속 형사입건했다고 밝혔다.

경찰에 따르면, 하나로텔레콤은 지난 2006년 1월부터 지난해 말까지 약 600만명에 달하는 개인정보 8530여만건을 전국 1000여개 텔레마케팅 회사에 넘겨준 혐의를 받고 있다.

특히 하나로텔레콤은 이 과정에서 모 은행과 신용카드 모집에 대한 업무제휴를 맺은 뒤 신용카드 발급을 위한 텔레마케팅 업체를 지정해 이용자 개인정보 96만건을 제공한 것으로 드러났다.

또한 안티바이러스 등 부가서비스 판매를 위해 제3자인 전국 수백개 텔레마케팅 회사에 개인정보를 넘기기도 했으며,

심지어 당연히 해지고객정보를 파기해야되는데도, 인터넷 초고속망 해지를 신청한 이용자들의 정보를 전국 텔레마케팅 모집업체에 넘겨 '하나TV'나 전화 서비스 등의 전화영업을 유도한 혐의도 받고 있다.

경찰은 이번 수사과정에서 많은 유선통신 가입자들이 각종 상품을 구입하라는 스팸광고 전화에 시달리고, 다른 통신사로 이미 옮겨간 이용자들에게 다시 자신들의 회사상품을 구입하라고 유도하는 등 해지고객들의 정보까지 사용하는 등 개인정보 침해가 도를 넘어섰다는 판단에 수사가 착수됐다고 설명했다.

경찰 관계자는 "이같은 개인정보 무단사용이 실적을 높이기 위한 일부 센터들의 독자적인 행위라고 하나로텔레콤측은 변명했으나, 수사결과 본사차원의 지시에 의한 것으로 밝혀졌다"며 "특히 개인정보를 배포하는 시스템을 개발해가며, 적극적으로 상품판매에 이용하라는 지시까지 했다"고 말했다.

경찰은 하나로텔레콤 외에 동의받지 않은 개인정보를 카드회사나 보험사 등 금융기관 텔레마케팅 영업에 제공한 증거를 잡고 모 통신사를 수사중이다.

특히 경찰은 옛 정보통신부와 통신위원회 직원들이 단속시 미리 조사일정, 대상 등 정보를 미리 흘리고 불법사실을 축소해 보고한 정황에 대해서도 사실을 확인할 예정이다.
728x90
728x90
1081만명 옥션 회원정보유출에 이어 유명 통신회사 하나로텔레콤이 600만명의 고객정보를 불법 사용한 정황이 드러나자 자신의 정보유출 여부를 확인하려는 이용자들이 늘고 있다.

하지만 아직 개인이 하나로텔레콤 홈페이지 등에서 자신의 정보유출 여부를 확인할 수 있는 방법은 없다.

하나로텔레콤 측은 "개인이 확인할 수 있는 시스템을 마련하는 계획은 잡혀있지 않다"고 밝혔다. 또 "옥션의 경우 해킹이므로 우리와 상황이 다르다"며 "회사의 공식 지침이 아직 정해지지 않았다"고 24일 말했다.

경찰은 2006년 1월1일부터 2007년 12월31일까지 하나로텔레콤의 초고속인터넷서비스에 가입한 적이 있는 고객 전부의 개인정보가 불법 무단판매된 것으로 보고 있다.

하나로텔레콤을 상대로 한 집단소송 움직임도 일고 있다. 소송을 준비하고 있는 녹색소비자연대 전국협의회은 "2006년 1월1일부터 2007년 12월31일 사이에 하나로통신의 초고속인터넷서비스에 가입했다는 사실을 입증할 수 있는 가입계약서나 확인서, 영수증, 계좌이체증명 등 관련서류를 첨부해야 참여할 수 있다"고 밝혔다.

이와 관련 하나로텔레콤 측은 "아직 검찰의 판단이 남아있다"며 "결과에 따라서 적절한 조치를 취할 것"이라는 입장이다.

서울지방경찰청 사이버범죄수사대는 23일 고객정보를 은행이나 텔레마케팅회사에 불법 제공한 혐의(정보통신망법 위반)로 하나로텔레콤 박병무 전 대표(47)와 전현직 지사장 22명을 불구속 형사입건했다고 밝혔다
728x90
728x90
변수 :
- 명사로 이름 짓는다. ( 변수는 data 자체를 가리키는 경우가 많다.)

- 명사로 사용할 수 없을 땐 명사화된 동사를 사용(ex: count)

- 변수이름의 첫글자는 영문 소문자로 시작

※ 헝가리언 노테이션 : type에 관한 정보를 이름에 포함시키는 방식으로 멤버변수의 경우 m_으로 시작하고, 포인터의 경우 이름 뒤에 _ptr... 뭐 이런 식의 작명법을 말한다. 이 책에서는 그러한 방법을 따르지 말라고 경고하고 있다. Win32와 MFC의 라이브러리에서 헝가리언 노테이션을 따르는 것이 대중적인 사용의 주된 이유지만 type에 관한 정보는 선언할 때 보는 것으로 충분하며 그러한 것들을 표시해줘야 할 정도라면 함수의 크기가 너무 커서 불편하다는 것이므로 나누라고 권한다.
단, type정보가 아니라 기능에 대한 정보라면 이름에 포함하는 것이 맞다. (index기능을 하는 변수를 idx_로 시작하기도 한다.)

※ 머리글자 조합 : 각 단어의 머리글자를 따서 이름짓는 방식이다. (예를 들어 SomeTypeWithMeaningfulNaming 라는 이름이 있다면 stwmn으로 줄이는 것이다. 일반적으로는 사전에 나오는 내용으로 구성하는 것이 원칙이다. 하지만 변수가 좁은 범위에서 사용된다면 너무 긴 이름 대신 짧은 이름으로 대치하고 주석을 달아두는 것도 좋다.


함수:
- 동사로 이름 짓는다.

- be, do, perform등과 같은 의미없는 동사의 사용은 피하라.

- 주의 : 사용자의 입장에서 생각하라
. 초보자들이 흔히 하는 실수로 함수의 입장에서 이름을 짓는 것이다. 항상 함수를 사용하는 사용자 입장에서 이름을 지어야 한다.  어떻게 해야할지 모르겠다면 왜 이 함수를 만드는지 생각해보자. 적절한 예시가 떠오르지 않는다. 이건 자꾸 연습하다 보면 저절로 될 것이다.

- 주의 : 함수의 내부적인 구현 방법은 생각하지 말고 그 함수의 역할을 생각하라. 함수는 하나의 기능만 가지고 있고 그 기능이 무엇인지에 대해서 이름을 짓는 것이다. 기능을 구현하기 위해 어떤 일을 하건 상관하지 마라. 사과가 몇개인지 알기 위해 사용하는 함수라고 하자. 그럴때 보통 int countApples(); 이런 식의 이름을 지을 것이다. 그러면 사과가 몇개인지만 알면 됐지 이 함수가 재귀호출을 하건 file을 건들건 쓰레드를 만들건 신경쓰지 말라는 말이다.

타입(클레스):
- 클레스 이름은 객체가 아니라 클레스를 묘사해야 한다.(사소하지만 중요한 차이: '사람'이란 클레스 이름대신 '홍길동'이란 클레스 이름을 사용한다면?)

- 상태 값을 가지는 객체를 묘사한다면 명사.

- 함수객체(functor : 함수들 만으로 구성된 객체로 static으로 구현되는 경우가 많다.)거나 가상 call back interface를 구현하는 클레스는 동사 or 잘 알려진 디자인 패턴의 이름

- 클레스가 위의 두가지 성격을 모두 가진다면 이름 정하기가 어렵고, 잘못된 설계일 가능성이 크다.

- DataObject와 같이 당연한 내용을 포함하는 이름은 좋지 않다.(클레스는 data를 포함하는 경우가 많고, 객체화 한다면 당연히 object가 되는 것이 아닌가! 그러니 중복해서 언급할 필요가 없다.) : 좋지 않은 단어 -> class, data, object, type
 

namespace, package:

- 전체적인 내용을 봐라. 이건 꽤 큰 범위라 어휘력에 맡긴다.

- 불필요한 부가적 설명은 피하라 : UI, filesystem, controls등과 같은 이름은 다 좋은 이름들이다. controls_group와 같이 이미 알고있는 내용을 덧붙이지 마라. 길고 쓸데없는 내용은 보기 싫다.

매크로:
= 매크로는 위험하다. (단순 무식 과격하며 힘도 엄청나게 쎄다 : 소스코드가 컴파일 되기 전에 전처리 단계에서 매크로에 해당하는 내용은 모두 지정된 매크로를 거친 값으로 바껴버린다.) 아주 위험하므로 반드시 눈에 띄는 표시가 필요하다.(#define 문을 생각하면 쉽다.)

- 모두 대문자로 표기 (그래야 눈에 잘 띈다)

- 충분히 독특한 이름을 사용해야 한다.(독특한 파일이름이나 프로젝트 이름을 접두사로 붙이는 것이 도움이 될수도 있다. 절대 다른 곳에서 실수로 같은 이름이나 그 이름이 포함된 이름을 사용하면 안된다.)

파일:
- 대소문자에 주의하라. 파일검색은 대소문자 구분을 무시하지만 대소문자를 구분해서 사용하는 곳이 분명히 있다. 책에서는 파일이름을 모두 소문자로 하는 것도 좋은 방법이라고 소개하고 있지만 JAVA에서는 클레스와 인터페이스 이름에 PropreCase를 사용하며 이 이름과 파일 이름이 같아야 제대로 작동한다.

- 헤더파일과 헤퍼의 내용을 구현한 파일의 이름은 같도록 해라. stack.hstack.cpp와 같이 쌍을 이루란 말이다.

- 여러 언어를 혼용해서 사용할 경우 같은 이름에 확장자가 다른 것은 같은 디렉토리에 두지 마라. stack.c, stack.cpp, stack.java가 한 디렉토리에 들어있다면 stack.o파일은 뭘 나타내는 것일까? 자식은 하난데 아빠가 셋이다. 가정에 큰일이 날 수도 있다.

- 확장자를 신경써라. C++에서는 확장자를 .C  .cc  .cpp  .cxx  .c++등 여러가지가 있으며 특이하게 헤더파일의 확장자가 .h대신 .hpp로 쓰이는 경우도 있단다. 이런 마구잡이로 쓰인 확장자는 꽤 거슬리는데 MS의 노예가 된 우리는 .cpp와 .h로 거의 통일되어 있다.

대문자 사용의 관례

일관성을 유지하라
- 하나의 이름에 다양한 규칙을 적용하는 바보는 없을 것이다. Using_underscores_AndProperCase 이런거나 Another_Case 같은 이름은 사용하면 안된다는 말이다.

- 프로젝트 전체에 일관된 규칙을 적용해야 한다.
다음과 같은 코드는 일관성이 없어 제대로 분석되기 어려울 것을 예감할 수 있다.
콘텍스트 활용
※ 범위(scope)
- 이름의 범위는 global, namespace, class, function(method), loop등 다양하다. 범위에 따라 이름이 조금씩 바뀔 수도 있다는 것을 참고하자. 같은 변수라고 해도 함수내에 사용되느냐 전역이냐에 따라 이름이 다르게 사용되는 예가 가끔 있다.

※ 타입(type)
- 위에서 이미 말했지만 type을 이름에 넣지 말라는 것이 Code Craft란 책의 주장이다. string형식의 변수에 address_string이란 이름을 주어 재언급을 하는 것은 피하자는 것이다. 헝가리언 노테이션은 이런 재언급을 목적으로 하고 있기 때문에 종종 비웃음 산다고 한다.)
그러나
내가 생각하기에 이 책의 저자는 구식 사고방식을 가지고 있는 것 같다. JAVA나 C#등과 같이 다양한 콤포넌트들이 구현되어 있고 그것들을 따와서 사용하는 방식의 프로그래밍은 객체의 형식을 모두 기억하기 어렵다.
윈도우 응용 프로그램을 예로 든다면 form하나에 들어가는 구성요소(label, textbox, button등)의 종류가 많으면 이것들을 다 기억하기 어려울 수가 있다. 대체로 이러한 구성요소들은 form이 생성될 때 같이 생성되어서 form이 사라질 때까지 운명을 함께하기 때문에 scope가 너무 크다. 함수 내에서 사용되는 변수들은 type을 사용하는 것이 오히려 거추장스럽지만 범위가 넓은 경우 이름에 포함시켜 주는 것이 맞는 것 같다.(필요하니까 주장하는 사람들이 있는거다.) 다만 어떤 경우에 type을 적어주고 어떤 경우에 뺄 것인지 명확하게 구분지어 놔야 한다.
scope가 작은 경우 빼는 것이 좋고, 넓은 경우 넣는 것이 좋지만 프로젝트 전체에서 형식을 통일시켜야 일관성이 유지되니 심각하게 고민해봐야 할 사항이다.

(나의 경우엔 type을 적지 않는 편이다. 요즘은 tool들이 좋아서 이름만 있으면 어떤 형식인지 다 알려주기 때문에 그닥 필요하지가 않다. tool에 지배당하고 있는건가?)
728x90
728x90

오라클은 종속된 테이블의 삭제를 방지하고 테이블에 유효하지 않은 데이타가 입력되는 것을 방지하기 위하여 constraint를 사용합니다.


1. constraint 지침

    1) 제약조건에 이름을 지정하지 않으면 Oracle server가 SYS_Cn의 형식으로 자동으로 이름을 생성합니다.

    2) 제약조건은 크게 테이블 레벨과 열 레벨로 정의할 수 있습니다.


2. constraint 정의 예제

    SQL> CREATE TABLE EXAMPLE(

                ID               NUMBER(6),

                NAME         VARCHAR2(20)    [CONSTRAINT NAME_CTR] NOT NULL,    

                                                                     ----> 열 레벨(제약조건 이름을 생략하면 시스템이 자동으로 이름 생성

                ...

               

                CONSTRAINT EXAMPLE_ID_PK PRIMARY KEY(ID));                          

                                                                     ----> 테이블 레벨(제약조건 이름이 EXAMPLE_ID_PK로 생성)


3. constraint 유형

    1) NOT NULL : 해당열에 널값이 없도록 하기 위한 제약조건

    2) UNIQUE : 지정된 열에 대해 널값은 허용하나, 동일한 값은 허용되지 않는 제약조건

                       오라클 서버는 지정된 열에 대해 자동으로 인덱스를 생성

                       [예제] SQL> ...CONSTRAINT EXAMPLE_ID_UK UNIQUE(ID)

    3) PRIMARY KEY : 테이블의 각 행을 식별하기 위해 테이블당 하나의 기본키를 생성

                                중복된 값과 널값을 가질 수 없다

                                오라클 서버는 지정된 열에 대해 자동으로 인덱스를 생성

    4) FOREIGN KEY : 동일한 테이블 또는 다른 테이블에서 기본키 또는 고유키를 참조하는 제약조건

                                부모 테이블의 값과 일치하거나 널값을 가져야 한다.

                                ON DELETE CASCADE : 부모 테이블의 행이 삭제되는 경우 자식 테이블의 종속 행을 삭제

                                ON DELETE SET NULL : 부모 테이블의 행이 삭제되는 경우 종속 외래키 값을 널로 변환

                                [예제] ...CONSTRAINT EXAMPLE_ID_FK FOREIGN KEY(ID) REFERENCES DEPT(ID)

    5) CHECK : 각 행이 만족시켜야 하는 조건을 정의

                      [예제] SAL       NUMBER(10)    CONSTRAINT EXAMPLE_SAL_CK

                                                                      CHECK(SAL > 1000)


4. constraint를 조회하는 데이타 딕셔너리

    1) USER_CONSTRAINTS

        테이블 생성 후 DESC로 테이블 구조를 보면 NOT NULL제약조건만 보이고, 다른 제약 조건은 보이지 않게 된다.

        이때 다른 제약조건을 보기 위해 USER_CONSTRAINTS라는 데이타 딕셔너리가 제공된다.

        여러 필드중 CONSTRAINT_TYPE이라는 필드만 살펴보도록 하겠다. 나머지는 쉽게 이해가 될 것이다.

        P : PRIMARY KEY, R : FOREIGN KEY, C : CHECK 또는 NOT NULL, U : UNIQUE

    2) USER_CONS_COLUMNS

        제약 조건 이름과 연관된 컬럼을 볼 수 있게 하는 데이타 딕셔너리


5.  constraint 추가 / 삭제

    1) constraint 추가

        EMP_TEST테이블의 DEPT_ID필드가  DETP_TEST의 ID값을 참조하는 제약조건을 추가하는 예문

        SQL> SELECT TABLE_NAME, CONSTRAINT_NAME FROM USER_CONSTRAINTS

                 WHERE TABLE_NAME IN('EMP_TEST','DETP_TEST');

                 TABLE_NAME                     CONSTRAINT_NAME

                 ------------------------------ -------------

                 EMP_TEST                         EMP_TEST_PK

 

        1) DETP_TEST테이블의 ID필드를 PRIMARY KEY값으로 설정

 

 

           SQL> ALTER TABLE DETP_TEST

                    ADD CONSTRAINT DETP_TEST_PK PRIMARY KEY(ID);

                    Table altered.

        2) EMP_TEST테이블의 DEPT_ID필드를 DETP_TEST의 ID값을 참조하는 FOREIGN KEY값으로 설정

                    ALTER TABLE EMP_TEST

                    ADD CONSTRAINT EMP_TEST_FK FOREIGN KEY(DEPT_ID) REFERENCES DETP_TEST(ID);

                    Table altered.

        3) constraint 추가 여부 확인

            SQL> SELECT TABLE_NAME, CONSTRAINT_NAME FROM USER_CONSTRAINTS

                     WHERE TABLE_NAME IN('EMP_TEST','DETP_TEST');

                     TABLE_NAME                     CONSTRAINT_NAME

                     ------------------------------ ------------------------------

                     DETP_TEST                      DETP_TEST_PK

                     EMP_TEST                        EMP_TEST_FK

                     EMP_TEST                        EMP_TEST_PK

 

    2) constraint 삭제

        EMP_TEST테이블의 DEPT_ID(FOREIGN KEY)필드의 제약조건을 삭제

        SQL> ALTER TABLE EMP_TEST

                 DROP CONSTRAINT EMP_TEST_FK;

                 Table altered.

       

        SQL> SELECT TABLE_NAME, CONSTRAINT_NAME FROM USER_CONSTRAINTS

                 WHERE TABLE_NAME IN('EMP_TEST','DETP_TEST');

                 TABLE_NAME                     CONSTRAINT_NAME

                 ------------------------------ ------------------------------

                 DETP_TEST                       DETP_TEST_PK

                 EMP_TEST                        EMP_TEST_PK

 

        DETP_TEST테이블의 ID필드의 제약조건(PRIMARY KEY)을 삭제

        SQL> ALTER TABLE DETP_TEST

                 DROP PRIMARY KEY CASCADE;     ----> CASCADE를 붙이면 FOREIGN KEY까지 동시에 삭제가 됨

                 Table altered.


        SQL> SELECT TABLE_NAME, CONSTRAINT_NAME FROM USER_CONSTRAINTS

                 WHERE TABLE_NAME IN('EMP_TEST','DETP_TEST');

                 TABLE_NAME                     CONSTRAINT_NAME

                 ------------------------------ ------------------------------

                 EMP_TEST                         EMP_TEST_PK

 

6. constraint의 enable/disable : 제약조건을 삭제/생성하지 않고도 제약조건을 비활성화 할 수 있다.

    1) constraint의 disable

        DETP_TEST테이블의 ID필드의 제약조건(PRIMARY KEY)을 disable

        SQL> ALTER TABLE DETP_TEST

                 DISABLE CONSTRAINT DETP_TEST CASCADE; ---> CASCADE는 FOREIGN KEY까지 동시에 disable됨

                 Table altered.


        SQL> SELECT TABLE_NAME, STATUS FROM USER_CONSTRAINTS

                 WHERE TABLE_NAME IN('EMP_TEST','DETP_TEST');

                 TABLE_NAME                     STATUS

                 ------------------------------ --------

                 DETP_TEST                      DISABLED

                 EMP_TEST                       DISABLED

                 EMP_TEST                       ENABLED


    2) constraint의 enable

        disable된 제약조건을 enable시키기 위해서는 PRIMARY KEY를 enable시킨 후, FOREIGN KEY를 enable 시켜

        야 한다.l

        SQL> ALTER TABLE DETP_TEST

                 ENABLE CONSTRAINT DETP_TEST;

                 Table altered.

        SQL> ALTER TABLE EMP_TEST

                  ENABLE CONSTRAINT EMP_TEST_FK;

                  Table altered.

        SQL> SELECT TABLE_NAME, STATUS FROM USER_CONSTRAINTS

                  WHERE TABLE_NAME IN('EMP_TEST','DETP_TEST');

                  TABLE_NAME                     STATUS  

                  ------------------------------ --------

                  DETP_TEST                      ENABLED

                  EMP_TEST                       ENABLED

                  EMP_TEST                       ENABLED

728x90

'Programming > DB매니아' 카테고리의 다른 글

MySQL 예약어  (0) 2008.02.26

+ Recent posts