GPT-3.5-Turbo 및 GPT-4 모델 작업

GPT-3.5-Turbo 및 GPT-4 모델은 대화형 인터페이스에 최적화된 언어 모델입니다. 모델의 동작은 이전 GPT-3 모델과 다릅니다. 이전 모델은 텍스트 입력 및 텍스트 출력이었습니다. 즉, 프롬프트 문자열을 수락하고 프롬프트에 추가하기 위해 완료를 반환했습니다. 그러나 GPT-3.5-Turbo 및 GPT-4 모델은 대화 입력 및 메시지 출력입니다. 모델은 특정 채팅과 같은 대화 기록 형식으로 형식화된 입력을 예상합니다. 채팅에서 모델이 작성한 메시지를 나타내는 완료를 반환합니다. 이 형식은 멀티 턴을 위해 특별히 설계되었지만 채팅이 아닌 시나리오에도 적합할 수 있습니다.

이 문서에서는 GPT-3.5-Turbo 및 GPT-4 모델을 시작하는 과정을 안내합니다. 최상의 결과를 가져오려면 여기에 설명된 기술을 사용합니다. 모델이 장황하고 덜 유용한 응답을 제공하는 경우가 있으므로 이전 모델 시리즈와 동일한 방식으로 모델과 상호 작용하려고 하지 마세요.

GPT-3.5-Turbo 및 GPT-4 모델 작업

다음 코드 조각은 채팅 완료 API와 함께 GPT-3.5-Turbo 및 GPT-4 모델을 사용하는 가장 기본적인 방법을 보여 줍니다. 이러한 모델을 프로그래밍 방식으로 처음 사용하는 경우 GPT-3.5-Turbo 및 GPT-4 빠른 시작부터 시작하는 것이 좋습니다.

참고 항목

Azure OpenAI 설명서에서는 GPT-3.5-Turbo 및 GPT-35-Turbo를 같은 의미로 언급합니다. OpenAI의 모델 공식 이름은 gpt-3.5-turbo입니다. Azure OpenAI의 경우 Azure 관련 문자 제약 조건으로 인해 기본 모델 이름은 gpt-35-turbo입니다.

import os
from openai import AzureOpenAI

client = AzureOpenAI(
  api_key = os.getenv("AZURE_OPENAI_API_KEY"),  
  api_version = "2024-02-01",
  azure_endpoint = os.getenv("AZURE_OPENAI_ENDPOINT")
)

response = client.chat.completions.create(
    model="gpt-35-turbo", # model = "deployment_name".
    messages=[
        {"role": "system", "content": "Assistant is a large language model trained by OpenAI."},
        {"role": "user", "content": "Who were the founders of Microsoft?"}
    ]
)

#print(response)
print(response.model_dump_json(indent=2))
print(response.choices[0].message.content)
{
  "id": "chatcmpl-8GHoQAJ3zN2DJYqOFiVysrMQJfe1P",
  "choices": [
    {
      "finish_reason": "stop",
      "index": 0,
      "message": {
        "content": "Microsoft was founded by Bill Gates and Paul Allen. They established the company on April 4, 1975. Bill Gates served as the CEO of Microsoft until 2000 and later as Chairman and Chief Software Architect until his retirement in 2008, while Paul Allen left the company in 1983 but remained on the board of directors until 2000.",
        "role": "assistant",
        "function_call": null
      },
      "content_filter_results": {
        "hate": {
          "filtered": false,
          "severity": "safe"
        },
        "self_harm": {
          "filtered": false,
          "severity": "safe"
        },
        "sexual": {
          "filtered": false,
          "severity": "safe"
        },
        "violence": {
          "filtered": false,
          "severity": "safe"
        }
      }
    }
  ],
  "created": 1698892410,
  "model": "gpt-35-turbo",
  "object": "chat.completion",
  "usage": {
    "completion_tokens": 73,
    "prompt_tokens": 29,
    "total_tokens": 102
  },
  "prompt_filter_results": [
    {
      "prompt_index": 0,
      "content_filter_results": {
        "hate": {
          "filtered": false,
          "severity": "safe"
        },
        "self_harm": {
          "filtered": false,
          "severity": "safe"
        },
        "sexual": {
          "filtered": false,
          "severity": "safe"
        },
        "violence": {
          "filtered": false,
          "severity": "safe"
        }
      }
    }
  ]
}
Microsoft was founded by Bill Gates and Paul Allen. They established the company on April 4, 1975. Bill Gates served as the CEO of Microsoft until 2000 and later as Chairman and Chief Software Architect until his retirement in 2008, while Paul Allen left the company in 1983 but remained on the board of directors until 2000.

참고 항목

다음 매개 변수는 새로운 GPT-35-Turbo 및 GPT-4 모델(logprobs, best_ofecho)에서 사용할 수 없습니다. 이러한 매개 변수 중 하나를 설정하면 오류가 발생합니다.

모든 응답에는 finish_reason이 포함됩니다. finish_reason에 가능한 값은 다음과 같습니다.

  • stop: API가 전체 모델 출력을 반환했습니다.
  • length: max_tokens 매개 변수 또는 토큰 제한으로 인해 모델 출력이 불완전합니다.
  • content_filter: 콘텐츠 필터의 플래그로 인해 콘텐츠가 생략됩니다.
  • null: API 응답이 아직 진행 중이거나 완료되지 않았습니다.

max_tokens를 300 또는 500과 같이 평소보다 약간 더 높은 값으로 설정하는 것이 좋습니다. 값이 높을수록 모델은 메시지 끝에 도달하기 전에 텍스트 생성을 중단하지 않습니다.

모델 버전 관리

참고 항목

버전 gpt-35-turbo는 OpenAI의 gpt-3.5-turbo 모델과 동등합니다.

이전 GPT-3 및 GPT-3.5 모델과 달리 gpt-35-turbo 모델과 gpt-4gpt-4-32k 모델은 계속 업데이트됩니다. 이러한 모델의 배포를 만들 때 모델 버전도 지정해야 합니다.

모델 페이지에서 해당 모델의 모델 사용 중지 날짜를 확인할 수 있습니다.

채팅 완료 API 작업

OpenAI는 대화형식의 입력을 허용하도록 GPT-35-Turbo 및 GPT-4 모델을 학습했습니다. message 매개 변수는 역할별로 구성된 대화가 포함된 메시지 개체 배열을 사용합니다. Python API를 사용하면 사전 목록이 사용됩니다.

기본 채팅 완료 형식은 다음과 같습니다.

{"role": "system", "content": "Provide some context and/or instructions to the model"},
{"role": "user", "content": "The users messages goes here"}

하나의 질문에 답변이 이어지는 대화는 다음과 같습니다.

{"role": "system", "content": "Provide some context and/or instructions to the model."},
{"role": "user", "content": "Example question goes here."},
{"role": "assistant", "content": "Example answer goes here."},
{"role": "user", "content": "First question/message for the model to actually respond to."}

시스템 역할

시스템 메시지라고도 하는 시스템 역할은 배열의 시작 부분에 포함됩니다. 이 메시지는 모델에 초기 지침을 제공합니다. 시스템 역할에서 다음과 같은 다양한 정보를 제공할 수 있습니다.

  • 도우미의 간략한 설명.
  • 도우미의 성격 특성.
  • 도우미가 따르기를 원하는 지침이나 규칙입니다.
  • 모델에 필요한 데이터 또는 정보(예: FAQ의 관련 질문).

사용 사례에 맞게 시스템 역할을 사용자 지정하거나 기본 지침을 포함할 수 있습니다. 시스템 역할/메시지는 선택 사항이지만 최상의 결과를 가져오려면 최소한 기본 역할/메시지를 포함하는 것이 좋습니다.

메시지

시스템 역할 뒤에는 userassistant 사이에 일련의 메시지를 포함할 수 있습니다.

 {"role": "user", "content": "What is thermodynamics?"}

모델에서 응답을 트리거하려면 도우미가 응답할 차례임을 나타내는 사용자 메시지로 끝납니다. 또한 퓨샷 학습을 수행하는 방법으로 사용자와 도우미 간 일련의 메시지 예를 포함할 수도 있습니다.

메시지 프롬프트 예

다음 섹션에서는 GPT-35-Turbo 및 GPT-4 모델과 함께 사용할 수 있는 다양한 스타일의 프롬프트 예를 보여 줍니다. 이러한 예는 단지 시작점일 뿐입니다. 다양한 프롬프트를 실험하여 고유의 사용 사례에 맞게 동작을 사용자 지정할 수 있습니다.

기본 예제

GPT-35-Turbo 모델이 chat.openai.com과 유사하게 작동하도록 하려면 Assistant is a large language model trained by OpenAI.와 같은 기본 시스템 메시지를 사용할 수 있습니다.

{"role": "system", "content": "Assistant is a large language model trained by OpenAI."},
{"role": "user", "content": "Who were the founders of Microsoft?"}

지침이 포함된 예

일부 시나리오에서는 모델이 수행할 수 있는 작업에 대한 가드 레일을 정의하기 위해 모델에 추가 지침을 제공할 수 있습니다.

{"role": "system", "content": "Assistant is an intelligent chatbot designed to help users answer their tax related questions.
Instructions: 
- Only answer questions related to taxes. 
- If you're unsure of an answer, you can say "I don't know" or "I'm not sure" and recommend users go to the IRS website for more information. "},
{"role": "user", "content": "When are my taxes due?"}

근거를 위한 데이터 사용

또한 시스템 메시지에 관련 데이터 또는 정보를 포함하여 대화를 위한 추가 컨텍스트를 모델에 제공할 수도 있습니다. 적은 양의 정보만 포함해야 하는 경우 시스템 메시지에 해당 정보를 하드 코딩할 수 있습니다. 모델이 유의해야 할 많은 양의 데이터가 있는 경우에는 포함을 사용하거나 또는 Azure AI Search와 같은 제품을 사용하여 쿼리 시 가장 관련성이 높은 정보를 검색할 수 있습니다.

{"role": "system", "content": "Assistant is an intelligent chatbot designed to help users answer technical questions about Azure OpenAI Serivce. Only answer questions using the context below and if you're not sure of an answer, you can say 'I don't know'.

Context:
- Azure OpenAI Service provides REST API access to OpenAI's powerful language models including the GPT-3, Codex and Embeddings model series.
- Azure OpenAI Service gives customers advanced language AI with OpenAI GPT-3, Codex, and DALL-E models with the security and enterprise promise of Azure. Azure OpenAI co-develops the APIs with OpenAI, ensuring compatibility and a smooth transition from one to the other.
- At Microsoft, we're committed to the advancement of AI driven by principles that put people first. Microsoft has made significant investments to help guard against abuse and unintended harm, which includes requiring applicants to show well-defined use cases, incorporating Microsoft’s principles for responsible AI use."
},
{"role": "user", "content": "What is Azure OpenAI Service?"}

채팅 완료를 사용하여 퓨샷 학습

모델에 퓨샷 예를 제공할 수도 있습니다. 새로운 프롬프트 형식으로 인해 퓨샷 학습에 대한 접근 방식이 약간 변경되었습니다. 이제 사용자와 도우미 간 일련의 메시지를 퓨샷 예로 프롬프트에 포함할 수 있습니다. 이러한 예를 사용하면 일반적인 질문에 대한 답변을 시드하여 모델을 준비하거나 모델에 특정 동작을 가르칠 수 있습니다.

이 예에서는 GPT-35-Turbo 및 GPT-4를 사용하여 퓨샷 학습을 사용하는 방법을 보여 줍니다. 다양한 접근 방식을 실험하여 사용 사례에 가장 적합한 접근 방식을 확인할 수 있습니다.

{"role": "system", "content": "Assistant is an intelligent chatbot designed to help users answer their tax related questions. "},
{"role": "user", "content": "When do I need to file my taxes by?"},
{"role": "assistant", "content": "In 2023, you will need to file your taxes by April 18th. The date falls after the usual April 15th deadline because April 15th falls on a Saturday in 2023. For more details, see https://www.irs.gov/filing/individuals/when-to-file."},
{"role": "user", "content": "How can I check the status of my tax refund?"},
{"role": "assistant", "content": "You can check the status of your tax refund by visiting https://www.irs.gov/refunds"}

비채팅 시나리오에 채팅 완료 사용

채팅 완료 API는 멀티 턴과 함께 작동하도록 설계되었지만 채팅이 아닌 시나리오에서도 잘 작동합니다.

예를 들어 엔터티 추출 시나리오의 경우 다음 프롬프트를 사용할 수 있습니다.

{"role": "system", "content": "You are an assistant designed to extract entities from text. Users will paste in a string of text and you will respond with entities you've extracted from the text as a JSON object. Here's an example of your output format:
{
   "name": "",
   "company": "",
   "phone_number": ""
}"},
{"role": "user", "content": "Hello. My name is Robert Smith. I'm calling from Contoso Insurance, Delaware. My colleague mentioned that you are interested in learning about our comprehensive benefits policy. Could you give me a call back at (555) 346-9322 when you get a chance so we can go over the benefits?"}

기본 대화 루프 만들기

지금까지의 예에서는 채팅 완료 API와 상호 작용하는 기본 메커니즘을 보여 줍니다. 이 예제에서는 다음 작업을 수행하는 대화 루프를 만드는 방법을 보여 줍니다.

  • 콘솔 입력을 지속적으로 사용하고 메시지 목록의 일부로써 사용자 역할 콘텐츠로 적절하게 서식을 지정합니다.
  • 콘솔에 출력되고 서식이 지정되어 메시지 목록에 도우미 역할 콘텐츠로 추가되는 응답을 출력합니다.

새로운 질문이 나올 때마다 지금까지의 대화 내용이 최신 질문과 함께 전송됩니다. 모델에는 메모리가 없으므로 각 새 질문이 제기될 때마다 업데이트된 대본을 보내야 합니다. 그렇지 않으면 모델은 이전 질문과 답변의 컨텍스트를 잃게 됩니다.

import os
from openai import AzureOpenAI

client = AzureOpenAI(
  api_key = os.getenv("AZURE_OPENAI_API_KEY"),  
  api_version = "2024-02-01",
  azure_endpoint = os.getenv("AZURE_OPENAI_ENDPOINT")  # Your Azure OpenAI resource's endpoint value.
)

conversation=[{"role": "system", "content": "You are a helpful assistant."}]

while True:
    user_input = input("Q:")      
    conversation.append({"role": "user", "content": user_input})

    response = client.chat.completions.create(
        model="gpt-35-turbo", # model = "deployment_name".
        messages=conversation
    )

    conversation.append({"role": "assistant", "content": response.choices[0].message.content})
    print("\n" + response.choices[0].message.content + "\n")

앞의 코드를 실행하면 빈 콘솔 창이 나타납니다. 창에 첫 번째 질문을 입력한 다음 Enter 키를 선택합니다. 응답이 반환되면 프로세스를 반복하여 계속 질문할 수 있습니다.

대화 관리

이전 예는 모델의 토큰 제한에 도달할 때까지 실행됩니다. 질문을 하고 답변을 받을 때 마다 messages 목록의 크기가 커집니다. gpt-35-turbo의 토큰 한도는 4,096 토큰입니다. gpt-4gpt-4-32k의 토큰 제한은 각각 8,192 및 32,768입니다. 이러한 한도에는 전송된 메시지 목록과 모델 응답 모두의 토큰 수가 포함됩니다. max_tokens 매개 변수 값과 결합된 메시지 목록의 토큰 수는 이러한 제한 내에서 유지되어야 합니다. 그렇지 않으면 오류가 발생합니다.

프롬프트와 완료가 토큰 제한 내에 있는지 확인하는 것은 사용자의 책임입니다. 더 긴 대화의 경우 토큰 수를 추적하고 한도 내에 속하는 프롬프트만 모델에 보내야 합니다.

참고 항목

한도를 초과할 수 있다고 판단되더라도 모든 모델에 대해 문서화된 입력 토큰 한도를 초과하지 않는 것이 좋습니다.

다음 코드 샘플에서는 OpenAI의 tiktoken 라이브러리를 사용하여 4,096 토큰 수를 처리하는 기술을 사용하는 간단한 채팅 루프 예를 보여 줍니다.

이 코드는 tiktoken 0.5.1을 사용합니다. 이전 버전이 있는 경우 pip install tiktoken --upgrade를 실행합니다.

import tiktoken
import os
from openai import AzureOpenAI

client = AzureOpenAI(
  api_key = os.getenv("AZURE_OPENAI_API_KEY"),  
  api_version = "2024-02-01",
  azure_endpoint = os.getenv("AZURE_OPENAI_ENDPOINT")  # Your Azure OpenAI resource's endpoint value.
)

system_message = {"role": "system", "content": "You are a helpful assistant."}
max_response_tokens = 250
token_limit = 4096
conversation = []
conversation.append(system_message)

def num_tokens_from_messages(messages, model="gpt-3.5-turbo-0613"):
    """Return the number of tokens used by a list of messages."""
    try:
        encoding = tiktoken.encoding_for_model(model)
    except KeyError:
        print("Warning: model not found. Using cl100k_base encoding.")
        encoding = tiktoken.get_encoding("cl100k_base")
    if model in {
        "gpt-3.5-turbo-0613",
        "gpt-3.5-turbo-16k-0613",
        "gpt-4-0314",
        "gpt-4-32k-0314",
        "gpt-4-0613",
        "gpt-4-32k-0613",
        }:
        tokens_per_message = 3
        tokens_per_name = 1
    elif model == "gpt-3.5-turbo-0301":
        tokens_per_message = 4  # every message follows <|start|>{role/name}\n{content}<|end|>\n
        tokens_per_name = -1  # if there's a name, the role is omitted
    elif "gpt-3.5-turbo" in model:
        print("Warning: gpt-3.5-turbo may update over time. Returning num tokens assuming gpt-3.5-turbo-0613.")
        return num_tokens_from_messages(messages, model="gpt-3.5-turbo-0613")
    elif "gpt-4" in model:
        print("Warning: gpt-4 may update over time. Returning num tokens assuming gpt-4-0613.")
        return num_tokens_from_messages(messages, model="gpt-4-0613")
    else:
        raise NotImplementedError(
            f"""num_tokens_from_messages() is not implemented for model {model}. See https://github.com/openai/openai-python/blob/main/chatml.md for information on how messages are converted to tokens."""
        )
    num_tokens = 0
    for message in messages:
        num_tokens += tokens_per_message
        for key, value in message.items():
            num_tokens += len(encoding.encode(value))
            if key == "name":
                num_tokens += tokens_per_name
    num_tokens += 3  # every reply is primed with <|start|>assistant<|message|>
    return num_tokens
while True:
    user_input = input("Q:")      
    conversation.append({"role": "user", "content": user_input})
    conv_history_tokens = num_tokens_from_messages(conversation)

    while conv_history_tokens + max_response_tokens >= token_limit:
        del conversation[1] 
        conv_history_tokens = num_tokens_from_messages(conversation)

    response = client.chat.completions.create(
        model="gpt-35-turbo", # model = "deployment_name".
        messages=conversation,
        temperature=0.7,
        max_tokens=max_response_tokens
    )


    conversation.append({"role": "assistant", "content": response.choices[0].message.content})
    print("\n" + response.choices[0].message.content + "\n")

이 예에서는 토큰 수에 도달한 후 대화 기록에서 가장 오래된 메시지가 제거됩니다. 효율성을 위해 pop() 대신 del이 사용됩니다. 항상 시스템 메시지를 보존하고 사용자 또는 도우미 메시지만 제거하기 위해 인덱스 1부터 시작합니다. 시간이 지남에 따라, 이 대화 관리 방법을 사용하면 모델이 대화의 이전 내용을 점차 잃어버리기 때문에 대화 품질이 저하될 수 있습니다.

또 다른 방식은 대화 기간을 최대 토큰 길이 또는 특정 턴 수로 제한하는 것입니다. 최대 토큰 제한에 도달한 후 대화를 계속하도록 허용하면 모델의 컨텍스트가 손실됩니다. 사용자에게 새 대화를 시작하라는 메시지를 표시하고 메시지 목록을 지워 사용 가능한 전체 토큰 한도로 새 대화를 시작할 수 있습니다.

앞에서 설명한 코드의 토큰 계산 부분은 OpenAI의 쿡북 예 중 하나의 간소화된 버전입니다.

문제 해결

다음은 문제 해결 팁입니다.

채팅 완료 엔드포인트에 ChatML 구문을 사용하지 마세요.

일부 고객은 채팅 완료 엔드포인트 및 최신 모델에서 레거시 ChatML 구문을 사용하려고 합니다. ChatML은 gpt-35-turbo 버전 0301 모델의 레거시 완료 엔드포인트에서만 작동하는 미리 보기 기능이었습니다. 이 모델은 사용 중지될 예정입니다. 최신 모델 및 채팅 완료 엔드포인트에서 ChatML 구문을 사용하려고 하면 오류가 발생하고 예기치 않은 모델 응답 동작이 발생할 수 있습니다. 이 사용을 권장하지 않습니다.

Error 원인 해결 방법
400 - "입력의 특수 토큰으로 인해 출력을 생성하지 못했습니다." 프롬프트에는 모델/엔드포인트에서 인식하거나 지원하지 않는 레거시 ChatML 토큰이 포함되어 있습니다. 프롬프트/메시지 배열에 레거시 ChatML 토큰이 포함되어 있지 않은지 확인합니다. 레거시 모델에서 업그레이드하는 경우 모델에 API 요청을 제출하기 전에 모든 특수 토큰을 제외합니다.

다음 단계