Users on my site all have a "home region" field. This profile field is saved for each user and used to customise various site features, so that the user gets shown local content.

These regions aren't states or cities - they're more like electorate / local council boundaries (I'm not really sure what the US analogy would be). Most users are going to be uncertain about which region they actually want to save to their user profile.

I have a form which allows users to either (A) explicitly select their region from a select dropdown or (B) enter their postcode, submit the form, and get back their region. This form works fine.

I want users to be able to pick a region at registration time using this form, and have that region saved to their profile. Ideally I'd like to integrate the "select region" form with the user_register form, so that they can submit the form, get told "you are part of X region" and then click "register" and create a new user account with that region.

What I'm doing is using hook_user() to insert my form elements, perform my extra validation and then try to save the region data to the user on submit.

EDIT: the below is roughly how I solved this

function mymodule_user($op, &$edit, &$account, $category = NULL) {
  /* add "select your region" functionality to the user edit form */
  $category = 'Regional information';
  switch ($op) {
    case 'register':
    case 'form':
        /* "register": The user account registration form is about to be displayed. The module should present the form elements it wishes to inject into the form. */
        /* "form": The user account edit form is about to be displayed. The module should present the form elements it wishes to inject into the form. */
        $form = array();
        $form['Regional information']['region'] = _region_select('', _region_select_options());
        $form['Regional information']['postcode'] = _postcode();
        return $form;
    case 'validate':
        /* "validate": The user account is about to be modified. The module should validate its custom additions to the user object, registering errors as necessary. */
        $region = $account['region'];
        $postcode = $account['postcode'];
        // form_set_error() if I need to
    case 'insert':
    case 'update':
        /* submit happens *before* the user account is saved - we want insert or update
           "insert": The user account is being added.  
           "update": The user account is being changed.
           The module should save its custom additions to the user object into the database and set the saved fields to NULL in $edit. */
        $region_code = $edit['region'];
        $postcode = $edit['postcode'];
        if (!$region_code && $postcode) { // pull the region from the postcode
        if ($region_code) {
            $region_term = taxonomy_get_term($region_code);
            $region_name = $region_term->name;
            /* the profile module wants the name of the region, not the id */
            $profile_edit = array( 'profile_region' => $region_name );
            profile_save_profile($profile_edit, $account, $category);

1 Answer 1


Do you think you could just make the select dropdown and postcode input box parts of the user_form? Looks like you've got the functionality working already, so it would be a matter of a simple module implementing the following hook:

  1. hook_user(register) to alter the registration form and add your custom fields. You'll want to use a profile or profile_taxonomy functionality to insert the form element
  2. hook_user(validate) to validate the user input (incorrect postcode etc.)
  3. hook_user(submit) to convert the postcode to region and to save that information in the user profile
  • thanks, this sounds much simpler than how I was planning on doing things. I'll give this a try and let you know how it works out.
    – George
    Jul 28, 2011 at 7:11
  • One think that makes it interesting is that the postcode form is potentially multistage - some postcodes are associated with multiple regions. I guess I've got to work out how to send the registration form back for another round.
    – George
    Jul 29, 2011 at 2:16
  • It would be cool if you could to it in-place. Place a button next to the postcode input that would submit the current postcode and via AHAH replace the select drop down with only appropriate list of regions. Have a look at the #ahah form control.
    – Jan Tomka
    Jul 29, 2011 at 3:26
  • thanks Jan, finally got around to sitting down and working this out. Your suggestion worked great.
    – George
    Aug 1, 2011 at 9:08

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.