While I search this one out on my own, may be some one could provide quick answer. Thank you so much in advance.
So i really enjoy google groups and how every member receives notification about all new things that happen in the group. All new topics, old topics, added replies and so on. But we need our own forum, so my group went with phpBB forum on our site.
I basically want my board to send out notifications to all members. So that members that are on the phone do not have to be present on the forum physically.
Any one faced this issue before, any quick solutions? Settings in phpBB that can address that right away. May be custom setting for groups?
==============================================================================
As I have found out, actually every user can subscribe to forums. Haven't been looking hard enough or just missed it. That produces desired effect for me. But so far I have no idea of a way to force that behavior for all users regardless of their actions. Which would be preferable for small board. But good news if this natively supported by phpBB i bet i can write some code to extend this feature.
The only thing I can think of is somehow forcing every member to subscriber to every applicable forum/thread. I would look to do this via a back-end query, not through anything phpBB provides.
After looking online at the phpBB schema, I propose the following query set to be run daily via a cron job:
insert into phpbb_forums_watch
select distinct f.forum_id, u.user_id, 0
from phpbb_forums f, phpbb_users u
where u.user_type = 0
and not exists (select 1 from phpbb_forums_watch
where forum_id = f.forum_id
and user_id = u.user_id);
insert into phpbb_topics_watch
select distinct t.topic_id, u.user_id, 0
from phpbb_topics t, phpbb_users u
where u.user_type = 0
and not exists (select 1 from phpbb_topics_watch
where topic_id = t.topic_id
and user_id = u.user_id);
Let me know what you think of this..
I also posted this question on phpBB forums: thats what I got -> http://www.phpbb.com/community/viewtopic.php?f=72&t=2106567&p=12877384#p12877384
there is apparently mod that is available.
thank you all for help.
Related
I have spent the better part of the morning looking for opinions on this issue - and while I noticed a lot of people stumble across it and post similar questions here, I was not really able to find a sufficient answer or solution. This must be such a wide-spread problem that I am either blind, or the question has never been fully discussed. I am using PHP, but the question is more or less primarily related to MySQL.
Imagine this MySQL query (just a random example):
SELECT
users.id,
users.firstname,
users.lastname,
GROUP_CONCAT(DISTINCT images.id, '|', images.url) as images
FROM
users
LEFT JOIN
assoc_users_images ON assoc_users_images.user_id = users.id
LEFT JOIN
images ON images.id = assoc_users_images.image_id
GROUP BY
users.id
The query should return all users with images that are connected to them via a connection table. Use case could be a social network where users are "tagged" on photos. At the moment, I am exploding the result for "images" in a PHP loop.
I chose this example because the amount of photos a user is tagged in could become extremely high and I just recently had the case where a whole application broke because I forgot to take into account the character limit for GROUP_CONCAT. So at least at this point I had the impression that GROUP_CONCAT is extremely hacky for what I want to do.
I wonder: What are better ways to solve this and to avoid GROUP_CONCAT at all? I know that MySQL can't return arrays, but there must be a way to solve this both efficient and elegantly?! Should I make another query? At which point? Should I query for images separately and bring everything together on the software side?
GROUP_CONCAT has a limitation indeed, but luckily you can change it, like
SET ##group_concat_max_len = 1000000;
If you want to permanently set its maximum value, then you will need to change it in the config, like
[mysqld]
group_concat_max_len=15360
I've been working on this for some hours now and it's getting tiring. I want to get users posts from people I follow and myself, just like twitter does.
So there's a table users_posts that has all users' posts with column user_id to determine who made the post.
Another table users_followers that contains all followers ie. user_id follows following_id
So here's my query:
User ID = 2271
SELECT users_followers.following_id AS following_id, users_posts.id
FROM users_followers, users_posts
WHERE users_posts.user_id = users_followers.following_id
AND (users_followers.user_id =2271)
This query works but the problem is, it's kinda slow. Is there a faster way to do this?
Also, as you can see, I can only get posts from those I follow, and not myself.
Any help?
If I'm understanding your tables properly, I would do this with an explicit JOIN. I'm not sure how much that would speed things up versus the implicit JOIN you're using though.
SELECT following_id, p.id
FROM users_followers f
LEFT JOIN users_posts p
ON (p.user_id = f.following_id)
WHERE f.user_id = 2271
Chances are, adding an index or two to your tables would help.
Using the MySQL EXPLAIN command (just put it in front of your SELECT query) will show the indexes, temporary tables, and other resources that are used for a query. It should give you an idea when one query is faster or more efficient than another.
Your query is fine as written, provided you have properly indexed your tables. At a minimum you need an index on users_posts.user_id and users_followers.following_id.
A query can also be slowed by large numbers of records, even when it is fully indexed. In that case, I find phpmyadmin to be an invaluable tool. From the server page (maybe localhost) select the Status tab to see a wealth of information about how your mysql server is performing and suggestions for how to improve it.
I am writing PHP application built on MySQL database made for 5-6 application sharing it. Because of that, I can not alter database structure, and I know many of you will say to do that first, but unfortunately I can't.
Here is my SQL fiddle of database schema, query that I am using, and desired output:
http://sqlfiddle.com/#!2/de7493/1
My solution is working on this example database, but on real production one, where some of these tables have more than 1m rows, when I try to run it my DB crash. Even if I cut down this sql to select only from 3-4 tables it will still crash. Maybe this is not possible to do, maybe I am doing it wrong. Here is what I have to do:
I am dynamically getting cpv_id from url. In my example, cpv_id is 66113000. Based on that value, I have to discover which club offers are related with that cpv_id. Then based on those offers I have to discover which club members are having some of those offers. ( club members are companies ). Then based on club member id, I have to discover some informations about company that is a member of the club, among that data I have to discover company special_id. And based on that special_id I have to read company reports.
So basically: based on cpv_id I have to discover company reports for the company having club offers related to that id ( simple right ? ). As you can see from the way my tables are related in SQLFiddle, I need to get through 6 tables to get what I really need. Once again, I can not alter database structure.
This is very complex thing going on, I am afraid that you will not understand what I need. I hope that SQLFiddle will help. And if you have any more questions please ask me.
So considering that my solution, my query, fail since database crash if I run it. Is there any way to get desired result ? Can I optimize this query somehow, or do I need to write some other one, or do anything else ? I am pretty lost, since I never had to go this deep and read data from so many tables just to get desired result.
Thanks,
Anita
This seems to do the same thing:
SELECT DISTINCT company_report.*
FROM company_report,
company,
users,
club,
club_offer,
club_offer_cpv
WHERE company_report.company_special_id = company.special_id AND
company.id = users.company_id AND
users.id = club.users_id AND
club.id = club_offer.club_id AND
club_offer.id = club_offer_id AND
club_offer_cpv.cpv_id = 66113000
Other people will prefer joins, but I find this easier to read, and they are equivalent. It would look something like this:
SELECT DISTINCT company_report.*
FROM company_report
JOIN company ON company_report.company_special_id = company.special_id
JOIN users ON company.id = users.company_id
JOIN club ON users.id = club.users_id
JOIN club_offer ON club.id = club_offer.club_id
JOIN club_offer_cpv ON club_offer.id = club_offer_id AND
club_offer_cpv.cpv_id = 66113000
Actually, that's not bad, I mean I might even prefer this last one.
Add index to your table relationships id's, then try to add one by one table using left outer joins
I have a list of events for example I wanna show on a page with the users that have created them which is all in a table and the user who has created them's unique id, now if I wanna show their username and avatar I would have to run 100 queries inorder to show 100 events! but I'm sure their is a easier way I don;t know!
i have a table (user_table) with fields user_id INT(8) and user_photo VARCHAR(255)
and I have another table (user_event_table) with event_id INT(8), event_user_id INT(8), event_details TEXT
so I want to show a list of all these events but I want to next to it show the user_photo !
Learn to join with SQL. It's fundamental to relational databases.
SELECT * FROM user_event_table uet
LEFT JOIN user_table ut
ON ut.user_id = uet.user_id
Now each record will have a username and photo string.
Show us your tables, along with the query you're currently using, in a different question and people will help you with the SQL.
Yes. Get the accurate current time at the start of your PHP script, and get the time at the end, and log the page name and the difference in times.
If you're worried about this, you need to conduct a security audit of your scripts. There's no easy way to tell what someone who has access to your page's contents will leak.
Again, you need a real security audit. Someone will have to read and understand all the code in order to be sure. There's no easy way.
I am just learning php as I go along, and I'm completely lost here. I've never really used join before, and I think I need to here, but I don't know. I'm not expecting anyone to do it for me but if you could just point me in the right direction it would be amazing, I've tried reading up on joins but there are like 20 different methods and I'm just lost.
Basically, I hand coded a forum, and it works fine but is not efficient.
I have board_posts (for posts) and board_forums (for forums, the categories as well as the sections).
The part I'm redoing is how I get the information for the last post for the index page. The way I set it up is that to avoid using joins, I have it store the info for latest post in the table for board_forums, so say there is a section called "Off Topic" there I would have a field for "forum_lastpost_username/userid/posttitle/posttime" which I woudl update when a user posts etc. But this is bad, I'm trying to grab it all dynamically and get rid of those fields.
Right now my query is just like:
`SELECT * FROM board_forums WHERE forum_parent='$forum_id''
And then I have the stuff where I grab the info for that forum (name, description, etc) and all the data for the last post is there:
$last_thread_title = $forumrow["forum_lastpost_title"];
$last_thread_time = $forumrow["forum_lastpost_time"];
$lastpost_username = $forumrow["forum_lastpost_username"];
$lastpost_threadid = $forumrow["forum_lastpost_threadid"];
But I need to get rid of that, and get it from board_posts. The way it's set up in board_posts is that if it's a thread, post_parentpost is NULL, if it's a reply, then that field has the id of the thread (first post of the topic). So, I need to grab the latest post_date, see which user posted that, THEN see if parentpost is NULL (if it's null then the last post is a new thread, so I can get all the info of the title and user there, but if it's not, then I need to get the info (title, id) of the first post in that thread (which can be found by seeing what post_parentpost is, looking up that ID and getting the title from it.
Does that make any sense? If so please help me out :(
Any help is greatly appreciated!!!!
Updating board___forums whenever a post or a reply is inserted is - regarding performance - not the worst idea. For displaying the index page you only have to select data from one table board_forums - this is definitely much faster than selecting a second table to get the "last posts' information", even when using a clever join.
You are better off just updating the stats on each action, New Post, Delete Post etc.
The other instances would not likely require any stats update (deletion of a thread would trigger a forum update, to show one less topic in the topic count).
Think about all the actions the user would do, in most cases, you dont need to update any stats, therefore, getting the counts on the fly is very inefficient and you are right to think so.
It looks like you've already done the right thing.
If you were to join, you'd do it like this:
SELECT * FROM board_forums
JOIN board_posts ON board_posts.forum_id = board_forums.id
WHERE forum_parent = '$forum_id'
The problem with that, is that it gets you every post, which is not useful (and very slow). What you would want to do is something like this
SELECT * FROM board_forums
JOIN board_posts ON board_posts.forum_id = board_forums.id ORDER BY board_posts.id desc LIMIT 1
WHERE forum_parent = '$forum_id'
except SQL doesn't work like that. You can't order or limit on a join (or do many other useful things like that), so you have to fetch every row and then scan them in code (which sucks).
In short, don't worry. Use joins for the actual case where you do want to load all forums and all posts in one hit.
The simple solution will result in numerous queries, some optional, as you're already discovered.
The classic approach to this is to cache the results, and only retrieve it once in a while. The cache doesn't have to live long; even two or three seconds on a busy site will make a significant difference.
De-normalizing the data into a table you're already reading anyway will help. This approach saves you figuring out optional queries and can be a bit of a cheap win because it's just one more update when an insert is already happening. But it shifts some data integrity to the application.
As an aside, you might be running into the recursive-query problem with your threads. Relational databases do not store heirarchical data all that well if you use a "simple" algorithim. A better way is something sometimes called 'set trees'. It's a bit hard to Google, unfortunately, so here are some links.