Need some guidance here…

Under Launch Instance, Networking tab, we have a custom Horizon version that 
also has a "Policy Profile" Checkbox field, in addition to the Network" 
MultipleChoiceList field.

Now, we'd like to be able to select a policy for each network selected.  The 
initial thought was to convert the Policy Profile Checkbox field into a 
MultipleChoiceList (If there is a better way to define these, please let us 
know!).  With the Network field, as the user drags and drops networks, they are 
associated with nic1, nic2, nic3… I was figuring the same thing could be done 
with the "Policy Profile". So…

I changed the field type and added a widget, the same as with the Network 
field. Then, I modified the populate function (and the contribute function, but 
I'm not quite sure yet how that plays into this). The code snippet looks like 
this:

class SetNetworkAction(workflows.Action):
    network = forms.MultipleChoiceField(label=_("Networks"),
                                        required=True,
                                        widget=forms.CheckboxSelectMultiple(),
                                        error_messages={
                                            'required': _(
                                                "At least one network must"
                                                " be specified.")},
                                        help_text=_("Launch instance with"
                                                    "these networks"))
    profile = forms.MultipleChoiceField(label=_("Policy Profiles"),
                                        required=False,
                                        widget=forms.CheckboxSelectMultiple(),
                                        help_text=_("Launch instance with "
                                                     "these policy profile(s)"))


    class Meta:
        name = _("Networking")
        permissions = ('openstack.services.network',)
        help_text = _("Select networks for your instance.")

    def populate_network_choices(self, request, context):
        try:
            tenant_id = self.request.user.tenant_id
            networks = api.quantum.network_list_for_tenant(request, tenant_id)
            for n in networks:
                n.set_id_as_name_if_empty()
            network_list = [(network.id, network.name) for network in networks]
            LOG.error("PCM Populating NETWORKS: %s" % network_list)
        except:
            network_list = []
            exceptions.handle(request,
                              _('Unable to retrieve networks.'))
        return network_list

    def populate_profile_choices(self, request, context):
        try:
            profiles = api.quantum.profile_list(request, 'policy')
            for p in profiles:
                p.set_id_as_name_if_empty()
            profile_list = [(p.id, p.name) for p in profiles]
            LOG.error("PCM Populating PROFILES: %s" % profile_list)
        except:
            profile_list = []
            exceptions.handle(request, _("Unable to retrieve profiles."))
        return profile_list


class SetNetwork(workflows.Step):
    action_class = SetNetworkAction
    template_name = "project/instances/_update_networks.html"
    contributes = ("network_id", "profile_id")

    def contribute(self, data, context):
        if data:
            networks = self.workflow.request.POST.getlist("network")
            # If no networks are explicitly specified, network list
            # contains an empty string, so remove it.
            networks = [n for n in networks if n != '']
            if networks:
                context['network_id'] = networks

            profiles = self.workflow.request.POST.getlist("profile")
            # If no profiles are explicitly specified, profile list
            # contains an empty string, so remove it.
            profiles = [p for p in profiles if p != '']
            if profiles:
                context['profile_id'] = profiles
            LOG.debug("PCM at contribute %d - %d" %(len(networks), 
len(profiles)))
        return context
        ...

I do see the populate functions called and there is data there. In the HTML 
template, I modified the row for the Policy Profile from using a 
"{{form.profile }}" to having the same code as the Network list field has. I 
created identical CSS definitions for the profile styles. Code looks like this:

<table class="table-fixed" id="networkListSortContainer">
  <tbody>
    <tr>
      <td class="actions">
        <h4 id="selected_network_h4">{% trans "Selected Networks" %}</h4>
        <ul id="selected_network" class="networklist">
        </ul>
        <h4>{% trans "Available networks" %}</h4>
        <ul id="available_network" class="networklist">
        </ul>
      </td>
      <td class="help_text">
          {% include "project/instances/_launch_network_help.html" %}
      </td>
    </tr>
    
    <tr>
      <td class="actions">
        <h4 id="selected_profile_h4">{% trans "Selected Profiles" %}</h4>
        <ul id="selected_profile" class="profilelist">
        </ul>
        <h4>{% trans "Available profiles" %}</h4>
        <ul id="available_profile" class="profilelist">
        </ul>
      </td>
      <td class="help_text">
          {% include "project/instances/_launch_profile_help.html" %}
      </td>
    </tr>
  </tbody>
</table>


When I try this, I see the choices for the "Available Networks" and I can drag 
and drop them to the "Selected Networks", but the "Available Profiles" list is 
empty. No box or anything shown, just the h4 headings. I did try having a 
second table, with id profileListSortedContainer, but the same results occurred.

BTW, if I rename the populate_network_choices to populate_policy_choices, and 
vice versa, I see the list of policies in the "Available Networks" and nothing 
still in the "Available Policies" field.

What am I missing/doing wrong, such that the policy choices information is not 
being filled out in the template?

How does the populate_policy_choices info get used in the template. I'm missing 
that part of things?

At a higher level, is there a better way to relate these two fields?  I still 
need to verify that for each network there needs to be one policy, and whether 
or not the policy choice needs to be unique (as in not having the same policy 
for multiple networks - which MAY be allowed - I need to check).

Thanks in advance!



PCM (Paul Michali)

MAIL p...@cisco.com
IRC   pcm_  (irc.freenode.net)
TW   @pmichali

_______________________________________________
OpenStack-dev mailing list
OpenStack-dev@lists.openstack.org
http://lists.openstack.org/cgi-bin/mailman/listinfo/openstack-dev

Reply via email to