Based on the code provided it looks like you are misunderstanding how wp_localize_script works. The signature of the function looks like this:
wp_localize_script( $handle, $name, $data );
Where $handle is the name of a JavaScript file you have registered or enqueued before calling wp_localize_script. Take a look at the example in the codex (I've added line numbers below):
1: <?php 2: 3: // Register the script 4: wp_register_script( 'some_handle', 'path/to/myscript.js' ); 5: 6: // Localize the script with new data 7: $translation_array = array( 8: 'some_string' => __( 'Some string to translate', 'plugin-domain' ), 9: 'a_value' => '10' 10: ); 11: wp_localize_script( 'some_handle', 'object_name', $translation_array ); 12: 13: // Enqueued script with localized data. 14: wp_enqueue_script( 'some_handle' );
Take a look at line 4 above. First a JavaScript file is registered with the $handle 'some_handle'.
Next, on line 11, wp_localize_script() is used to register the localization data for the script handle 'some_handle' registered on line 4.
Finally, on line 14, the JavaScript file (registered on line 4) is enqueued. Because wp_localize_script() was passed the same $handle registered on line 4, WordPress automatically includes the localized data on every page that wp_enqueue_script( 'some_handle' ); is called.
In other words, you need to use wp_localize_script with a registered JavaScript file. Not by itself like you are doing currently.
This quote from the notes section says more or less the same thing:
IMPORTANT! wp_localize_script() MUST be called after the script has been registered using wp_register_script() or wp_enqueue_script().
Also, I don't think you need to json_encode() your $data. WordPress should do that for you.