Skip to content

FEATURE: Add shard key support#413

Merged
jhpark816 merged 1 commit into
naver:developfrom
ing-eoking:shard
Dec 24, 2025
Merged

FEATURE: Add shard key support#413
jhpark816 merged 1 commit into
naver:developfrom
ing-eoking:shard

Conversation

@ing-eoking

Copy link
Copy Markdown
Collaborator

🔗 Related Issue

  • jam2in/arcus-works#790

⌨️ What I did

  • 샤드키 기능을 추가합니다.
    • 샤드키 기능을 사용하는 경우, hash_with_namespace 기능 사용 여부 관계없이 무조건 namespace + key 문자열을 해싱합니다.

@ing-eoking

Copy link
Copy Markdown
Collaborator Author

CI 실패는 최근 반영된 gat로 인하여 실패합니다.

@ing-eoking ing-eoking marked this pull request as draft December 18, 2025 07:54
@ing-eoking ing-eoking force-pushed the shard branch 2 times, most recently from 23b893c to 7b9ae0b Compare December 19, 2025 06:44
@ing-eoking ing-eoking marked this pull request as ready for review December 19, 2025 06:49
@ing-eoking ing-eoking marked this pull request as draft December 19, 2025 06:50
Comment thread libmemcached/hash.cc Outdated
size_t namespace_length= memcached_array_size(ptr->_namespace);

if (temp_length >= MEMCACHED_MAX_KEY)
if (namespace_length + key_length >= MEMCACHED_MAX_KEY)

@ing-eoking ing-eoking Dec 19, 2025

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

너무 큰 키에 대해 0번 서버만 선택하도록 하는 방식은 조금 부자연스러운 것 같습니다.
나중에 별도 이슈로 처리하도록 하겠습니다.

@ing-eoking ing-eoking marked this pull request as ready for review December 19, 2025 07:03
@jhpark816

Copy link
Copy Markdown
Contributor

@namsic 리뷰 바랍니다.

@namsic namsic left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@jhpark816 jhpark816 left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

리뷰 완료

Comment thread libmemcached/hash.cc Outdated
return 0;

if (ptr->flags.hash_with_namespace)
if (ptr->flags.hash_with_namespace || ptr->flags.enable_shard_key)

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

enable_shard_key 시에 key 문자열을 copy하여 처리하는 것은 불필요합니다.

Comment thread docs/user-guide/02-arcus-c-client.md Outdated
하지만 키의 일부만을 기준으로 해싱하고 싶다면, 이 기능을 활성화하면 된다.

이 기능을 사용하면, 키에서 `{`와 `}` 사이에 있는 값만을 기준으로 해싱을 수행한다.
만약 `{` 또는 `}` 중 하나라도 없거나 값이 지정되지 않은 경우에는 기존과 마찬가지로 전체 키를 해싱하게 된다.

@jhpark816 jhpark816 Dec 23, 2025

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

아래 내용으로 변경합시다.

캐시 클러스터에서 특정 데이터가 어느 노드에 저장될지는 기본적으로 키 전체를 해싱하여 결정한다.

키의 일부만을 기준으로 해싱하고 싶다면, 아래와 같이MEMCACHED_BEHAVIOR_ENABLE_SHARD_KEY 기능을 활성화하여야 하고, 해싱 대상이 되는 키의 일부를 {} 문자로 감싸서 지정하면 된다. 만약 {} 문자로 키의 일부를 지정하지 않았다면, 기존대로 전체 키를 해싱한다.

@ing-eoking

Copy link
Copy Markdown
Collaborator Author

@jhpark816

수정되었습니다.

Arcus-C-Client에서는 서버로 전송할 명령어를 구성할 때 다음과 같은 형식을 사용합니다.

struct libmemcached_io_vector_st vector[]=
{
  { strlen(command), command },
  { memcached_array_size(ptr->_namespace), memcached_array_string(ptr->_namespace) },
  { key_length, key },
  { 2, "\r\n" }
};

이 과정에서 key 앞에는 항상 namespace 문자열이 붙어 전송됩니다.
기본 설정에서는 namespace가 클러스터 내 서버 노드를 선택하기 위한 해싱 과정에 포함되지 않으며,
HASH_WITH_NAMESPACE 옵션을 활성화하면 namespace 역시 해싱 대상에 포함됩니다.

또한, namespace 값은 HASH_WITH_NAMESPACE 설정과 무관하게 사용자가 언제든지 지정하거나 변경할 수 있습니다.

@jhpark816 jhpark816 left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

리뷰 완료

Comment thread libmemcached/hash.cc Outdated
key= get_shard_key(key, key_length, &key_length);
}

return generate_hash(ptr, key, key_length);

@jhpark816 jhpark816 Dec 23, 2025

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

generate_hash() 함수의 구현에 shard key 찾는 기능이 들어가면 좋겠습니다.

static inline uint32_t generate_hash(const memcached_st *ptr, const char *key, size_t key_length)
{
  if (ptr->flags.enable_shard_key)
  {
    key= get_shard_key(key, key_length, &key_length);
  }
  return hashkit_digest(&ptr->hashkit, key, key_length);
}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@ing-eoking
코드를 다시 확인해 봐도,
위의 코드처럼 generate_hash()에서 shard key를 가져오는 것이 괜찮을 것 같습니다.

그리고, 기존 코드는 아래 부분만 변경하시죠. (주석 추가해서요)

 if (ptr->flags.hash_with_namespace)
=>
 // if (ptr->flags.hash_with_namespace)
 if (memcached_array_size(ptr->_namespace) > 0) // hashing with namespace in ARCUS.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

수정되었습니다.

Comment thread libmemcached/hash.cc Outdated
size_t namespace_length= memcached_array_size(ptr->_namespace);

if (temp_length >= MEMCACHED_MAX_KEY)
if (namespace_length > 0 && (ptr->flags.hash_with_namespace || ptr->flags.enable_shard_key))

@jhpark816 jhpark816 Dec 23, 2025

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

아래와 같이 기존 코드가 변경되어야 하지 않나 생각합니다.

//if (ptr->flags.hash_with_namespace)
size_t namespace_length= memcached_array_size(ptr->_namespace);
if (namespace_length > 0) { // hash with namespace in ARCUS.
  char temp[MEMCACHED_MAX_KEY];
  if (namespace_length + key_length >= MEMCACHED_MAX_KEY)
    return 0;

  strncpy(temp, memcached_array_string(ptr->_namespace), namespace_length);
  strncpy(temp + namespace_length, key, key_length);
   return generate_hash(ptr, temp, namespace_length + key_length);
} else {
   return generate_hash(ptr, key, key_length);
}

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

수정되었습니다.

@jhpark816 jhpark816 left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

리뷰 완료

Comment thread libmemcached/hash.cc Outdated
key= get_shard_key(key, key_length, &key_length);
}

return generate_hash(ptr, key, key_length);

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@ing-eoking
코드를 다시 확인해 봐도,
위의 코드처럼 generate_hash()에서 shard key를 가져오는 것이 괜찮을 것 같습니다.

그리고, 기존 코드는 아래 부분만 변경하시죠. (주석 추가해서요)

 if (ptr->flags.hash_with_namespace)
=>
 // if (ptr->flags.hash_with_namespace)
 if (memcached_array_size(ptr->_namespace) > 0) // hashing with namespace in ARCUS.

@jhpark816 jhpark816 merged commit 4bc7dfd into naver:develop Dec 24, 2025
1 check failed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants