Do the fields (structure) of MySQL tables get unique ids? - php

I'm not talking about unique keys or auto_increments, suppose I have this structure:
mysql> describe email_notifications;
+---------------+------------------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+---------------+------------------+------+-----+---------+----------------+
| email_id | int(11) unsigned | NO | PRI | NULL | auto_increment |
| email_address | varchar(100) | NO | | | |
| course_id | int(11) unsigned | NO | MUL | NULL | |
+---------------+------------------+------+-----+---------+----------------+
I'm building (for fun, practice, and hopefully some practical use) a tool in PHP that will analyze the structure of each table in a database and then compare it to a newer one (to assist in Dev -> Live updates), and then spit out some MySQL queries (Such as ALTER TABLE...) that I can run on the live database in order to bring it up to speed.
The question - does each field get a unique id of some sort?
If I change email_address from varchar(100) to text (for example) or the name course_id to cr_id, is there any way for me to tell that it's still technically the same dataset? I don't want to run a Delete and Add, but instead rename it give it a new type.
Or if there's a better way to do it without some sort of MySQL ID, that would be great :)
Thanks!

I think you can use information_schema.columns. The following are both unique keys in this table (even if they are not so defined):
TABLE_CATALOG, TABLE_SCHEMA, TABLE_NAME, COLUMN_NAME
TABLE_CATALOG, TABLE_SCHEMA, TABLE_NAME, ORDINAL_POSITION
When you change the name or type of a column, I do not believe that ORDINAL_POSITION is affected. So, the second version may be what you are looking for.
This may then lead to the question "what if I change the name of a table?" The information_schema tables can't help there, unfortunately.

Related

Know the last modified row or id's row in a mysql table

I'm using Mysql 5.5 and by example I have a table like this
+------------+-------------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+------------+-------------+------+-----+---------+----------------+
| idgroups | int(11) | NO | PRI | NULL | auto_increment |
| group_id | int(11) | YES | | NULL | |
| group_name | varchar(45) | YES | | NULL |
Where some people are allowed to do inserts,update and delete but I want to know which is the last modified row or row's id in a given time
Any ideas?
Thanks in advance
My suggestion would be to create a second table. something like edit_history for recording modifications. You can put triggers on your groups table above that says "Any time a record is inserted, deleted, or updated, create a record in my edit_history table".
A trigger can be created as follows:
CREATE TRIGGER trigger_name
AFTER INSERT
ON table_name FOR EACH ROW
BEGIN
-- For each row inserted
-- do something...
END;
Since your field is auto_increment, you can just select the maximum value of idgroups to get the most recently inserted value:
select max(idgroups) from tbl
to get last modified in general will require additional structure to your table. In particular, if you are deleting, you will need to store what you have most recently deleted somewhere.

How to get column description using PDO?

How to get column description using PDO? AS far as i understood fetchColumn and getColumnMeta does not return description field, which is part of MySQL database table.
I would like to write code as general as possible, thus i use PDO, which connects to all possible databases. Most probably description field is not available in all databases, thus there is no general function for retrieving it?
You can try :
$table_fields = $dbh->query("DESCRIBE tablename")->fetchAll();
It will return you all the column names of the table .
Or if you want it MySQL's side, you can try :
SHOW COLUMNS FROM <table_name> WHERE Field = ?
+-------+---------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+-------+---------+------+-----+---------+----------------+
| id | int(11) | NO | PRI | NULL | auto_increment |
+-------+---------+------+-----+---------+----------------+

PHP/MYSQL: Storing a list or massive table

I am still new to PHP and I was wondering which alternative would be better or maybe someone could suggest a better way.
I have a set of users and I have to track all of their interactions with posts. If a users taps on a button, it will add the post to a list and if they tap it again, it will remove the post, so would it be better to:
Have a column of a JSON array of postIDs stored in the table for each user (probably thousands).
-or-
Have a separate table with every save (combination of postID and userID) (probably millions) and return all results where the userID's match?
For the purposes of this question, there are two tables: Table A is users and Table B is posts. How should I store all of the user's saved posts?
EDIT: Sorry, but I didn't mention that posts will have multiple user interactions and users will have multiple post interactions (Many to Many relationship). I think that would affect Bob's answer.
This is an interesting question!
The solution really depends on your expected use case. If each user has a list of posts they've tagged, and that is all the information you need, it will be expedient to list these as a field in the user's table (or in their blob if you're using a nosql backend - a viable option if this is your use case!). There will be no impact on transmission time since the list will be the same size either way, but in this solution you will probably save on lookup time, since you're only using one table and dbs will optimize to keep this information close together.
On the other hand, if you have to be able to query a given post for all the users that have tagged it, then option two will be much better. In the former method, you'd have to query all users and see if each one had the post. In this option, you simply have to find all the relations and work from there. Presumably you'd have a user table, a post table and a user_post table with foreign keys to the first two tables. There are other ways to do this, but it necessitates maintaining multiple lists and cross checking each time, which is an expensive set of operations and error-prone.
Note that the latter option shouldn't choke on 'millions' of connections, since the db should be optimized for this sort of quick read. (pro tip: index the proper columns!) Do be careful about any data massage, though. One unnecessary for-loop will kill your performance.
For the purposes of this question, there are two tables: Table A is users and Table B is posts. How should I store all of the user's saved posts?
If each user has a unique ID of some sort (primary key), then ad a field to each post that refers to the unique ID of the user.
mysql> describe users;
+----------+------------------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+----------+------------------+------+-----+---------+----------------+
| id | int(11) unsigned | NO | PRI | NULL | auto_increment |
| email | varchar(200) | YES | | NULL | |
| username | varchar(20) | YES | | NULL | |
+----------+------------------+------+-----+---------+----------------+
mysql> describe posts;
+---------+------------------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+---------+------------------+------+-----+---------+----------------+
| id | int(11) unsigned | NO | PRI | NULL | auto_increment |
| user | int(11) unsigned | NO | | NULL | |
| text | text | YES | | NULL | |
+---------+------------------+------+-----+---------+----------------+
Then to get posts for a user, for example:
SELECT text
FROM posts
WHERE user=5;
Or to get all the posts from a particular organization:
SELECT posts.text,users.username
FROM posts,users
WHERE post.user=users.id
AND users.email LIKE '%#example.com';
I think it would make sense to keep a third table that would be all the post status data.
If your user interface shows, say, 50 posts per page, then the UI only needs to keep track of 50 posts at a time. They'll all have unique IDs in your database, so that shouldn't be a problem.

Speed Up MySQL (MyISAM) COUNTs with WHERE Clauses

We are implementing a system that analyses books. The system is written in PHP, and for each book loops through the words and analyses each of them, setting certain flags (that translate to database fields) from various regular expressions and other tests.
This results in a matches table, similar to the example below:
+------------------------+--------------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+------------------------+--------------+------+-----+---------+----------------+
| id | bigint(20) | NO | PRI | NULL | auto_increment |
| regex | varchar(250) | YES | | NULL | |
| description | varchar(250) | NO | | NULL | |
| phonic_description | varchar(255) | NO | | NULL | |
| is_high_frequency | tinyint(1) | NO | | NULL | |
| is_readable | tinyint(1) | NO | | NULL | |
| book_id | bigint(20) | YES | | NULL | |
| matched_regex | varchar(255) | YES | | NULL | |
| [...] | | | | | |
+------------------------+--------------+------+-----+---------+----------------+
Most of the omitted fields are tinyint, either 0 or 1. There are currently 25 fields in the matches table.
There are ~2,000,000 rows in the matches table, the output of analyzing ~500 books.
Currently, there is a "reports" area of the site which queries the matches table like this:
SELECT COUNT(*)
FROM matches
WHERE is_readable = 1
AND other_flag = 0
AND another_flag = 1
However, at present it takes over a minute to fetch the main index report as each query takes about 0.7 seconds. I am caching this at a query level, but it still takes too long for the initial page load.
As I am not very experienced in how to manage datasets such as this, can anyone advise me of a better way to store or query this data? Are there any optimisations I can use with MySQL to improve the performance of these COUNTs, or am I better off using another database or data structure?
We are currently using MySQL with MyISAM tables and a VPS for this, so switching to a new database system altogether isn't out of the question.
You need to use indexes, create them on the columns you do a WHERE on most frequently.
ALTER TABLE `matches` ADD INDEX ( `is_readable` )
etc..
You can also create indexes based on multiple columns, if your doing the same type of query over and over its useful. phpMyAdmin has the index option on the structure page of the table at the bottom.
Add multi index to this table as you are selecting by more than one field. Below index should help a lot. Those type of indexes are very good for boolean / int columns. For indexes with varchar values read more here: http://dev.mysql.com/doc/refman/5.0/en/create-index.html
ALTER TABLE `matches` ADD INDEX ( `is_readable`, `other_flag`, `another_flag` )
One more thing is to check your queries by using EXPLAIN {YOUR WHOLE SQL STATEMENT} to check which index is used by DB. So in this example you should run query:
EXPLAIN ALTER TABLE `matches` ADD INDEX ( `is_readable`, `other_flag`, `another_flag` )
More info on EXPLAIN: http://dev.mysql.com/doc/refman/5.0/en/explain.html

What is a Parent table and a Child table in Database?

I just want to know what is a parent table and what is a child table in databases. Can you please show me an example so I understand how it works please.
Thank You
Child tables and parent tables are just normal database tables, but they’re linked in a way that's described by a parent–child relationship.
It’s usually used to specify where one table’s value refers to the value in another table (usually a primary key of another table).
For example, imagine a news article. This could be represented by a table called articles and has fields for id, headline, body, published_date and author. But instead of placing a name in the author field, you could instead put the ID value of a user in a separate table—maybe called authors—that has information on authors such as id, name, and email.
Therefore, if you need to update an author’s name, you only need to do so in the authors (parent) table; because the articles (child) table only contains the ID of the corresponding author record.
Hope this helps you understand better.
Be aware you can have relationships that appear to be parent-child but are not, for instance when lookup tables are being used. The distinction is that in a true parent-child relationship, records typically don't stand are their own very well - they are detail records for the parent and are not useful without the parent table info. A person can own multiple cars in the DMV database, but you wouldn't want records in the CARS table without a parent record in the OWNERS table - it would be nearly useless data.
On the other hand, if I am using a lookup table to expand a code to something more meaningful, or to constrain data entry to acceptable values, then the "child" record can still useful (can stand alone) if the lookup table is deleted. I could still have the sex information as "M" or "F" even if I no longer have the lookup table to expand that to "Male" or "Female".
Parent - The entity on the "one" (/1) side of a relation with another table
Child - The entity on the "many" (/N/*) side of a relation with another table
A child table tends to be one where it has one or more foreign keys pointing at some other table(s). Note that a child table can itself be a parent to some OTHER table as well.
Those terms are used in database relationships.
for example u have two table,
1.Manifast
+-------------+------------------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+-------------+------------------+------+-----+---------+----------------+
| manifast_id | int(11) unsigned | NO | PRI | NULL | auto_increment |
| description | text | NO | | NULL | |
| title | text | NO | | NULL | |
+-------------+------------------+------+-----+---------+----------------+
day_sequence
+-----------------+------------------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+-----------------+------------------+------+-----+---------+----------------+
| day_sequence_id | int(11) unsigned | NO | PRI | NULL | auto_increment |
| day_number | int(11) | NO | | NULL | |
| day_start | int(11) | NO | | NULL | |
| manifast_id | int(11) | NO | | NULL | |
+-----------------+------------------+------+-----+---------+----------------+
if u want to connect those two tables,u need to use the command with following format.
> ALTER TABLE child_table_name ADD FOREIGN KEY (P_ID) REFERENCES
> parent_table_name (P_ID)
and so it become.
> ALTER TABLE day_sequence ADD CONSTRAINT fk_manifast FOREIGN KEY
> (manifast_Id) REFERENCES manifast(manifast_Id);
In summary,
Child table is a table which has foreign key,and is connected from others table.
Parent table has no foreign key and connect to other.
[ Note : This ans is just for connecting two tables ]

Categories