Does memcache retain information until flush? - php

The question title basically says it all..
If I perform:
$Cache = new Memcache;
$Cache->connect('HOST');
$Cache->set('Information', 'array(
"Testing" => "Value,
"Anther_Test" => "Another Value"
)');
and leave the information there, would the information be flushed/deleted after an interval?
or will it retain within the server until I call:
$Cache->flush();

What #hakre wrote in a comment plus you should get how to use cache.
Cache is not a date storage, it is a cache. You should never relay on what is there and what is not.
Typically you have a limit of a cache size and when it gets full it purges old values.
Typical usage case:
function get_something() {
$Cache = new Memcache;
$something = $Cache->get('something');
if ($something === false) {
$something = //get from db, prepare or whatever
$Cache->set('something', $something);
}
return $something;
}
TLDR; no

Related

How to insert same `datetime` variable into different tables?

I'd like to store a datetime variable into different tables by using two functions. I use constraint in CI but still have no luck.
This is the constraint:
$date_now = date("ymdhis");
define('TODAY_DATE',$date_now);
These are the functions:
public function save_activity_m(){
foreach($details as $rows){
$stock_in = $rows['product']."_".TODAY_DATE;
$data['STOCK_IN'] = ($rows['product'] == "") ? NULL : $stock_in;
$this->MProduct->ins_product_m($data);
}
echo "<script type='text/javascript'>alert('New stock arrived');window.top.location.reload();</script>";
}
public function save_notifikasi(){
$lampiran = $this->input->post('lamp');
$data['note_date'] = $lampiran."_".TODAY_DATE;
$data['note'] = $this->input->post('isi');
$this->MProduct->ins_notif($data);
echo "<script type='text/javascript'>alert('You have a notification');</script>";
}
How to make the datetime is the same for $data['STOCK_IN'] and $data['note_date']?
Since the web is stateless, no data in a PHP variable will be held from one page (or load) to another; essentially you're booting the application from scratch each time.
The only way around this is to use some sort of semi-persistent storage such as a cookie or session variable (or persistent storage like the database) - setting a constant, e.g. define('TODAY_DATE',$date_now); will only make that data constant for the current execution of the script(s).
This is a basic example using session storage ($_SESSION):
<?php
// crank up the session
// you may well have one running already,
// in which case ignore this
session_start();
// store the execution time for this script
// as a session variable if it's NOT already set
// i.e. don't overwrite it
if(empty($_SESSION['time_now'])) $_SESSION['time_now'] = date("ymdhis");
public function save_activity_m() {
foreach($details as $rows) {
$stock_in = $rows['product'] . "_" . $_SESSION['time_now'];
$data['STOCK_IN'] = ($rows['product'] == "") ? NULL : $stock_in;
$this->MProduct->ins_product_m($data);
}
echo "<script type='text/javascript'>alert('New stock arrived');window.top.location.reload();</script>";
}
/**
* Assuming this is the last thing you want to
* do with 'time_now' you should unset it here
*/
public function save_notifikasi() {
$lampiran = $this->input->post('lamp');
$data['note_date'] = $lampiran . "_" . $_SESSION['time_now'];
$data['note'] = $this->input->post('isi');
$this->MProduct->ins_notif($data);
// since we're done with the 'time_now' session
// variable we need to unset it...
unset($_SESSION['time_now']);
echo "<script type='text/javascript'>alert('You have a notification');</script>";
}
// just to be on the safe side unset the 'time_now' session var
// if it's older than 1 minute - otherwise future calls to this
// script, by the same user, during the same session will use
// the stored value from $_SESSION['time_now']
if(isset($_SESSION['time_now'])) {
$sessionTime = DateTime::createFromFormat('ymdhis', $_SESSION['time_now']);
$oneMinuteAgoTime = new DateTime('-1 minute');
if($sessionTime < $oneMinuteAgoTime) {
unset($_SESSION['time_now']);
}
}
The caveat is that because you've stored the time in a session variable, unless you update or unset it, it will always be there (for the current session) - so if the user runs the script again it'll just use the stored time from the session.
I've put in a couple of unset() calls to try and work around this.
See PHP: define. It's a constant and it should have the same value if the two functions executed in the same time the script is running.

Remove double qoutes when saving - pear/Config_Lite

Below is my Save Configuration file:
<?php
require_once 'Config/Lite.php';
$config = new Config_Lite();
$config->read('/var/www/html/svnmanager/Config/testing');
$config->set('/lol', 'user', 'JohnDoe')
->set('/lol', 'password', 'lemo')
->set('db2', 'user', '');
// set with ArrayAccess
$config['general'] = array('lang' => 'fr');
echo $config;
$config->save();
?>
and following is the output:
debug = ""
[db]
user = "JohnDoe"
password = "d0g1tcVs$HgIn1"
[db2]
user = ""
password = "d0g1tcVs$HgIn1"
[general]
lang = "fr"
[/lol]
user = "JohnDoe"
password = "ddada"
How do remove the double qoutes when saving the file?
for example:
[/lol]
user = JohnDoe
password = ddada
Add
$config->setQuoteStrings(false);
before saving it to the file
I'm going to start off with a rant: You are always better off using FLOSS libraries as intended/documented rather than hacking them to do what you want, if at all possible - even when the code is the only documentation available. For example, if a new version of Config_Lite comes out and you upgrade to that, you'll have "lost" your fixes.
(And, as if to prove my point, version 0.2.0 was released today at http://pear.php.net/package/Config_Lite/download/0.2.0)
To be more specific to answering your question, you need to call the setQuoteStrings method before you either explicitly save the .ini file output to a file using the write method or do anything that treats $config as a string value.
Typically, I'd do things in this order:
Create the [config] object first.
Set whatever options applicable (such as turning off quoted strings in this case)
Call whatever other methods as required (e.g. set values to sections etc)
Use resultant object (e.g. save the .ini file)
tl;dr:
$config = ....
$confg->setQuoteStrings(false);
$config->set(...);
echo $config;
$config->save();
Found myself a solution. You need to change the protected $quoteStrings = true; to protected $quoteStrings = false; in your Lite.php file :)

Set cookie fails for first time but works on refresh

Though after reading explanations about setting cookie and not working for first time i find it difficult to resolve the below problem as am new to php and cookies.
I have a webpage with for (e.g) cp.php, login.php, header.php, maindata.php , bottom.php. Whenever i login to the webpage cp.php will be processed from there 1.header.php will be called first 2.maindata.php will be called and 3.bottom.php will be called.
So am setting my cookie at maindata.php and the code is like,
<?php
$cid = $_GET["id"];
$XmlPath = $_GET["path"];
$numpath = $_GET["numpath"];
$finepath =$_GET["finepath"];
$Tech =$_GET["tech"];
$read_str="";
function read($Path)
{
$temp="";
if(file_exists($Path))
{
$library = new SimpleXMLElement($Path,null,true);
foreach($library->children("SAS") as $info){
foreach($info->children("SAS") as $attributes){
$nameVal = $attributes->Name."=".$attributes->Value;
$str_temp .=$nameVal."#";
}
}
}else
{
$str_temp ="NA";
}
return $str_temp;
}
$arrpath =explode(",",$XmlPath);
/*Reading and storing arrpath[0] has the path of xml to be parsed*/
$strG=read($arrpath[0]);
$strC=read($arrpath[1]);
$strB =read($arrpath[2]);
setcookie($cid.'strE',$strG);
setcookie($cid.'comstr',$strC);
setcookie($cid.'basstr',$strB);
(....)
in the same file am reading the cookie using the below code,
$read_str =$_COOKIE[$cid.'strE'].$_COOKIE[$cid.'comstr'].$_COOKIE[$cid.'basstr'];
after this process is done bottom.php will be called and for the first time loading is completed.As i said for the first time am not getting any value in $read_str, but if i refresh the page and do all the process again i am getting the value.
As SETCOOKIE will return TRUE incase of successfully setting cookie i tried putting it in an if-loop and it returned false even for the first time.
kindly assist me in finding where the problem exists!
Make use of isset to check if a cookie exists and then try setting one.
Something like this.
if(!isset($_COOKIE['yourcookie'])) {
setcookie('yourcookie', 'Some data !');
$_COOKIE['yourcookie'] = 'Some data !';
}
echo $_COOKIE['yourcookie'];
I arrived here looking for an answer as well. Here's the deal.
When you set a cookie it can only be accessed on the next page load, that is why you can't access it after you set it. If you really need to work with the cookie data right away, you could set the value directly in global cookie such as:
$_COOKIE['my_cookie'] = 'i am a cookie';
Use setcookie()just the same so you can set expiration, domain, etc..

mongoDB wont allow me to update

Ok this issue is driving me nutts, I thought that _id was meant to be ObjectID while the first time it inserts it does it correctly when I try to update it using the _id it does not work.
here is my code
//Save Data
function savedata($data){
$collection = $this->db->retail_logs;
$this->data = $data;
if($this->data['_id'] == NULL || $this->data['_id'] == "")
{
$this->data['_id'] = new MongoId();
}
else
{
$this->data['_id'] = ObjectID($this->data['_id']);
}
try {
$collection->update(
array("_id"=>$this->data['_id']),
$this->data, // new lead document to insert
array("upsert" => true, "safe" => true)
);
print $this->data['_id'];
} catch (Exception $e) {
print "we are not able to update";
}
}
i have tried to do the followinf
if($this->data['_id'] == NULL || $this->data['_id'] == "")
{
$this->data['_id'] = new MongoId();
}
else
{
$this->data['_id'] = ObjectID($this->data['_id']);
}
but that seems not to help.
What Is happening is it inserts the first time correctly with ObjectID(idnumber)
then when it goes to update is removes the ObjectID() and inserts a new lead with the same idnumber as before
so it looks like "IDNUMBER"
Your original code is close, but if you want to make a string _id the correct ObjectID type, use:
$this->data['_id'] = new MongoId($this->data['_id']);
Checking the Outcome of an Update Request
A non-upsert update may or may not modify an existing object. An upsert will either modify an existing object or insert a new object. The client may determine if its most recent message on a connection updated an existing object by subsequently issuing a getlasterror command ( db.runCommand( "getlasterror" ) ). If the result of the getlasterror command contains an updatedExisting field, the last message on the connection was an update request. If the updatedExisting field's value is true, that update request caused an existing object to be updated; if updatedExisting is false, no existing object was updated. An "upserted" field will contain the new _id value if an insert is performed (new as of 1.5.4)
Can you run the command as suggested by Mongo Docs and let us know the result of the command
Reference: Mongo Updating

delete cache by prefix in apc / memcache / eaccelerator

Let's assume I have these variables saved in apc, memcached and eaccelerator:
article_1_0
article_1_1
article_3_2
article_3_3
article_2_4
How can I delete all cached variables that starts with article_3_ (they can reach up to 10000) ?
is there any way to list the cached variables ?
The slow solution
For APC:
$iterator = new APCIterator('user', '#^article_3_#', APC_ITER_KEY);
foreach($iterator as $entry_name) {
apc_delete($entry_name);
}
For eaccelerator:
foreach(eaccelerator_list_keys() as $name => $infos) {
if (preg_match('#^article_3_#', $name)) {
eaccelerator_rm($name);
}
}
For memcached, look at #rik's answer
The proper solution
The general solution for expiring multiple keys at once is to namespace them. For expiring them, you just have to change the namespace:
Say you have a group of keys "article_3_1", "article_3_2", .... You can store them like this:
$ns = apc_fetch('article_3_namespace');
apc_store($ns."_article_3_1", $value);
apc_store($ns."_article_3_2", $value);
Fetch them like this:
$ns = apc_fetch('article_3_namespace');
apc_fetch($ns."_article_3_1");
And expire them all by just incrementing the namespace:
apc_inc('article_3_namespace');
Although the docs say APCIterator is available in apc >= 3.1.1, I'm on several systems that claim to have apc 3.1.9, however there is no APCIterator present. If you don't have APCIterator at your disposal, give something like this a whirl:
$aCacheInfo = apc_cache_info('user');
foreach($aCacheInfo['cache_list'] as $_aCacheInfo)
if(strpos($_aCacheInfo['info'], 'key_prefix:') === 0)
apc_delete($_aCacheInfo['info']);
In this example we're checking for a prefix in the key, but you could use preg_match et. al and achieve something closer to what APCIterator provides.
There is a way to retrieve all keys from memcache but it's very expensive.
If there is possibility to use alternatives for memcached, scache supports structured keyspaces. With it you could store data to nested paths :
scache_shset($conn, 'article/1/0', $data10);
scache_shset($conn, 'article/3/0', $data30);
scache_shset($conn, 'article/3/1', $data31);
and eventually destroy data by deleting the parent node
scache_shunset($conn, 'article/3');
There is an APCIterator which helps you search through the keys in APC.
Instantiate the APCIterator.
APCIterator::valid() means that there are keys still to iterate trough. APCIterator::key() returns you the apc key. APCIterator::next() moves the iterator position to the next item.
// APC
$iterator = new APCIterator('user', '/^article_3_/');
while($iterator->valid()) {
apc_delete($iterator->key());
// You can view the info for this APC cache value and so on by using
// $iterator->current() which is array
$iterator->next();
}
For memcache you can use Memcached and use getAllKeys method
// Memcached
$m = new Memcached();
$m->addServer('mem1.domain.com', 11211);
$items = $m->getAllKeys();
foreach($items as $item) {
if(preg_match('#^article_3_#', $item)) {
$m->delete($item);
}
}

Categories